2012-10-09 28 views
2

我的文件有以下格式加載數據:MySQL的,最有效的方式從解析的文件

Table1; Info 
rec_x11;rec_x21;rec_x31;rec_x41 
rec_x12;rec_x22;rec_x32;rec_x42 
... 
\n 
Table2; Info 
rec_x11;rec_x21;rec_x31;rec_x41 
rec_x12;rec_x22;rec_x32;rec_x42 
... 
\n 
Table3; Info 
rec_x11;rec_x21;rec_x31;rec_x41 
rec_x12;rec_x22;rec_x32;rec_x42 
... 

每批從TableX的頭部之後的下一行開始,用一個空行分隔符結束的記錄是大約700-800線的大小。

每一個這樣的批次線(rec_xyz ...)的需要導入到該批次的標題註明的有關的MyISAM表名(TableX

我熟悉的選項管道使用shell命令將流轉換爲LOAD DATA命令。

我感興趣的是簡單的java snipet代碼,它將解析這個文件,並且每次執行LOAD DATA一批記錄(在for循環中,也許使用seek命令)。

現在我試圖用IGNORE LINES跳過處理的記錄,但我不熟悉是否有一個選項可以忽略BELOW中的行?

是否有更有效的方式來解析和加載這種類型的文件到數據庫?

編輯

我已閱讀,JDBC支持輸入流LOAD DATA從5.1.3開始,我可以用它來遍歷文件的輸入流,每一次改變LOAD DATA聲明?

+0

你可以做,將添加在另一個'LOAD命令DATA'每個表的搜索和替換? – Kermit

回答

1

我附上我的代碼作爲溶液,

該溶液是基於additional functionalitysetLocalInfileInputStream)由MySQL連接/ J 5.1.3和以後添加。

我將管道輸入流轉換爲LOAD DATA INTO聲明,而不是使用直接文件URL。

附加信息:我使用BoneCP作爲連接池

public final void readFile(final String path) 
     throws IOException, SQLException, InterruptedException { 
    File file = new File(path); 

    final Connection connection = getSqlDataSource().getConnection(); 
    Statement statement = SqlDataSource.getInternalStatement(connection.createStatement()); 

    try{ 
     Scanner fileScanner = new Scanner(file); 
     fileScanner.useDelimiter(Pattern.compile("^$", Pattern.MULTILINE)); 

     while(fileScanner.hasNext()){ 
      String line; 
      while ((line = fileScanner.nextLine()).isEmpty()); 

      InputStream is = new ByteArrayInputStream(fileScanner.next().getBytes("UTF-8")); 
      String [] tableName = line.split(getSeparator()); 
      setTable((tableName[0]+"_"+tableName[1]).replace('-', '_')); 

      String sql = "LOAD DATA LOCAL INFILE '" + SingleCsvImportBean.getOsDependantFileName(file) + "' " 
        + "INTO TABLE " + SqlUtils.escape(getTable()) 
        + "FIELDS TERMINATED BY '" + getSeparator() 
        + "' ESCAPED BY '' LINES TERMINATED BY '" + getLinefeed() + "' "; 
      sql += "(" + implodeStringArray(getFields(), ", ") + ")";  
      sql += getSetClause(); 

      ((com.mysql.jdbc.Statement) statement).setLocalInfileInputStream(is); 
      statement.execute(sql);   
     } 
    }finally{ 
     statement.close(); 
     connection.close(); 
    } 
} 
+0

提到https://stackoverflow.com/questions/34826934/fast-import-data-to-mysql-in-java/34827006#34827006然而,我的問題是相同的情況下,我的數據庫是在Linux上,我的Java代碼運行Windows然後加載數據文件查詢失敗,任何替代任何人? – user2176576

相關問題