2010-04-08 2 views
5

BULK INSERT를 사용하여 플랫 파일에서 SQL Server에 대량의 데이터를로드하려고합니다. 그러나, 내 파일의 열 수는 다양합니다. 예를 들어 첫 번째 행에 14가 들어 있고 두 번째 행에 4가 들어 있습니다. 괜찮습니다. 최대 열 수의 테이블을 만들어서 파일을 NULL로 채우고 싶습니다. 열이 없습니다. 나는 그 시점부터 그걸 가지고 놀 수 있습니다. 그러나 SQL Server가 행의 끝에 도달하여 대상 테이블의 동일한 행을 채우기 위해 더 많은 열을 가질 경우 다음 행으로 넘어 가서 해당 행의 데이터를 잘못된 열로 놓으려고합니다. 탁자.일치하지 않는 열 수의 BULK INSERT

내가 찾는 동작을 얻는 방법이 있습니까? 이것을 지정하는 데 사용할 수있는 옵션이 있습니까? 누구도 전에 이것에 빠졌습니까?

여기에 코드

BULK INSERT #t 
FROM '<path to file>' 
WITH 
(
    DATAFILETYPE = 'char', 
    KEEPNULLS, 
    FIELDTERMINATOR = '#' 
) 

답변

3

BULK INSERT는 특별히 유연하지 않습니다. 한 가지 해결 방법은 하나의 큰 varchar 열을 포함하는 중간 테이블에 각 데이터 행을로드하는 것입니다. 일단로드되면, 자신의 루틴을 사용하여 각 행을 구문 분석합니다.

0

당신의 필드 종결과 함께 행 종결을 지정하는 시도이다. 이에

BULK INSERT #t 
FROM '<path to file>' 
WITH 
( 
    DATAFILETYPE = 'char', 
    KEEPNULLS, 
    FIELDTERMINATOR = '#', 
    ROWTERMINATOR = '\n' --Or whatever signifies the end of a row in your flatfile. 
) 

더 많은 정보는 여기에서 찾을 수 있습니다 :

http://msdn.microsoft.com/en-us/library/ms191485.aspx

+1

간단히 열 수를 변화 작동하지 않습니다 – gbn

1

컬럼의 다양한 수의 그것이 대량 삽입 코드에 의해 구문 분석 할 수 없음을 의미합니다. 정확한 열 수는 어떻게 알 수 있습니까? 너무 많은 것을 공급한다면 어떨까요?

4 열이있는 테이블에 업로드하고 나중에 나머지 (또는 하나의 큰 열)를 나눠야합니다 또는 동일한 수의 열을 생성하기 위해 사전 처리하십시오.

2

다른 해결 방법은 파일을 사전 처리하는 것입니다. T-SQL을 사용하여 행을 구문 분석하는 것보다 BULK가 제대로로드 될 수 있도록 각 행에 종결자를 추가하는 작은 독립 실행 형 프로그램을 작성하는 것이 더 쉽습니다.

다음은 VB6/VBA의 예입니다. 확실히 SQL Server 대량 삽입만큼 빠르지는 않지만 10 초 안에 91000 개의 행을 사전 처리했습니다.

Sub ColumnDelimiterPad(FileName As String, OutputFileName As String, ColumnCount As Long, ColumnDelimiter As String, RowDelimiter As String) 
    Dim FileNum As Long 
    Dim FileData As String 

    FileNum = FreeFile() 
    Open FileName For Binary Access Read Shared As #FileNum 
    FileData = Space$(LOF(FileNum)) 
    Debug.Print "Reading File " & FileName & "..." 
    Get #FileNum, , FileData 
    Close #FileNum 

    Dim Patt As VBScript_RegExp_55.RegExp 
    Dim Matches As VBScript_RegExp_55.MatchCollection 

    Set Patt = New VBScript_RegExp_55.RegExp 
    Patt.IgnoreCase = True 
    Patt.Global = True 
    Patt.MultiLine = True 
    Patt.Pattern = "[^" & RowDelimiter & "]+" 
    Debug.Print "Parsing..." 
    Set Matches = Patt.Execute(FileData) 

    Dim FileLines() As String 
    Dim Pos As Long 
    Dim MissingDelimiters 

    ReDim FileLines(Matches.Count - 1) 
    For Pos = 0 To Matches.Count - 1 
     If (Pos + 1) Mod 10000 = 0 Then Debug.Print Pos + 1 
     FileLines(Pos) = Matches(Pos).Value 
     MissingDelimiters = ColumnCount - 1 - Len(FileLines(Pos)) + Len(Replace(FileLines(Pos), ColumnDelimiter, "")) 
     If MissingDelimiters > 0 Then FileLines(Pos) = FileLines(Pos) & String(MissingDelimiters, ColumnDelimiter) 
    Next 
    If (Pos + 1) Mod 10000 <> 0 Then Debug.Print Pos + 1 

    If Dir(OutputFileName) <> "" Then Kill OutputFileName 
    Open OutputFileName For Binary Access Write Lock Read Write As #FileNum 
    Debug.Print "Writing " & OutputFileName & "..." 
    Put #FileNum, , Join(FileLines, RowDelimiter) 
    Close #FileNum 
    Debug.Print "Done." 
End Sub 
2

내 해결 (T-SQL에서 테스트) :

  1. 가 콜럼 수 = 가져 오기 파일의 최소 열 수와 테이블을 작성
  2. 실행 대량 삽입 (지금 성공)

마지막 표 열에는 항목 분리 기호를 포함한 나머지 항목 (

)이 있습니다.

당신에게 불필요한 경우, 다른 전체 열 테이블을 만들고 첫 번째 테이블의 모든 열을 복사 한 다음 마지막 열에 대해서만 약간의 구문 분석을 수행하십시오.

예제 파일

alpha , beta , gamma 
one , two , three , four 

테이블에 다음과 같이 표시됩니다

c1  | c2  | c3 
"alpha" | "beta" | "gamma" 
"one" | "two" | "three , four" 
관련 문제