2014-01-17 7 views
2

У меня есть файл .tsv, который содержит 39 столбцов . Последний, но один столбец содержит данные в виде строки, длина которой превышает 100 000 символов. Теперь, что происходит, когда я пытаюсь читать файл строка 1 имеет заголовок и затем данные следуетПропуск альтернативных строк при чтении файла .tsv

то, что происходит его после того, как линия 1 считывая переходит в линию 3, то линия 5, то линия 7 Хотя все строки имеют одинаковые данные читает журнал я получаю

lineNo=3, rowNo=2, customer=503837-100 , last but one cell length=111275 
lineNo=5, rowNo=3, customer=503837-100 , last but one cell length=111275 
lineNo=7, rowNo=4, customer=503837-100 , last but one cell length=111275 
lineNo=9, rowNo=5, customer=503837-100 , last but one cell length=111275 
lineNo=11, rowNo=6, customer=503837-100 , last but one cell length=111275 
lineNo=13, rowNo=7, customer=503837-100 , last but one cell length=111275 
lineNo=15, rowNo=8, customer=503837-100 , last but one cell length=111275 
lineNo=17, rowNo=9, customer=503837-100 , last but one cell length=111275 
lineNo=19, rowNo=10, customer=503837-100 , last but one cell length=111275 

След. M у Код:

import java.io.FileReader; 
import org.supercsv.cellprocessor.Optional; 
import org.supercsv.cellprocessor.constraint.NotNull; 
import org.supercsv.cellprocessor.ift.CellProcessor; 
import org.supercsv.io.CsvBeanReader; 
import org.supercsv.io.ICsvBeanReader; 
import org.supercsv.prefs.CsvPreference; 

public class readWithCsvBeanReader { 
    public static void main(String[] args) throws Exception{ 
     readWithCsvBeanReader(); 
    } 


private static void readWithCsvBeanReader() throws Exception { 

    ICsvBeanReader beanReader = null; 

    try { 

     beanReader = new CsvBeanReader(new FileReader("C:\MAP TSV\abc.tsv"), CsvPreference.TAB_PREFERENCE); 
     // the header elements are used to map the values to the bean (names must match) 
     final String[] header = beanReader.getHeader(true); 
     final CellProcessor[] processors = getProcessors(); 
     TSVReaderBrandDTO tsvReaderBrandDTO = new TSVReaderBrandDTO(); 

     int i = 0; 
     int last = 0; 

     while((tsvReaderBrandDTO = beanReader.read(TSVReaderBrandDTO.class, header, processors)) != null) { 
      if(null == tsvReaderBrandDTO.getPage_cache()){ 
       last = 0; 
      } 
      else{ 
       last = tsvReaderBrandDTO.getPage_cache().length(); 
      } 
      System.out.println(String.format("lineNo=%s, rowNo=%s, customer=%s , last but one cell length=%s", beanReader.getLineNumber(), 
       beanReader.getRowNumber(), tsvReaderBrandDTO.getUnique_ID(), last)); 
      i++; 
     } 

     System.out.println("Number of rows : "+i); 

    } 
    finally { 
     if(beanReader != null) { 
      beanReader.close(); 
     } 
    } 
} 

private static CellProcessor[] getProcessors() { 

    final CellProcessor[] processors = new CellProcessor[] { 
     new Optional(), new NotNull(), new NotNull(), new NotNull(), new NotNull(), 
     new NotNull(), new NotNull(), new NotNull(), new NotNull(), new NotNull(), 
     new NotNull(), new NotNull(), new NotNull(), new NotNull(), new NotNull(), 
     new NotNull(), new NotNull(), new NotNull(), new NotNull(), new NotNull(), 
     new NotNull(), new NotNull(), new NotNull(), new NotNull(), new NotNull(), 
     new NotNull(), new NotNull(), new NotNull(), new NotNull(), new NotNull(), 
     new NotNull(), new NotNull(), new NotNull(), new NotNull(), new NotNull(), 
     new NotNull(), new NotNull(), new NotNull(), new Optional()}; 

     return processors; 
    } 
} 

Пожалуйста, дайте мне знать, где я буду неправильно

ответ

0

Я проверил http://supercsv.sourceforge.net/examples_reading.html. Посмотрите внимательно на Пример CSV-файла и Выход. Не может ли быть так, что ваши строки содержат неэкранированный знак " (двойной апостроф), поэтому парсер считает, что запись данных охватывает две физические линии?

Если вы не используете двойной апостроф символ как символ кавычки, вы можете изменить CsvPreference - см http://supercsv.sourceforge.net/apidocs/org/supercsv/prefs/CsvPreference.html - так что двойные кавычки не рассматривается как символ кавычки:

CsvPreference MY_PREFERENCES = new CsvPreference.Builder(
    SOME_NEVER_USED_CHARACTER, ',', "\r\n").build(); 

Конечно для вкладок разделителями использования CSV-то вроде этого:

CsvPreference MY_PREFERENCES = new CsvPreference.Builder(
    SOME_NEVER_USED_CHARACTER, '\t', "\r\n").build(); 

Обратитесь к CsvPreference Javadoc для подписи Builder и изменить фактические значения соответственно.

+0

Ya Honza, вы правы, у него есть неэкранированный «... можете ли вы предложить какой-либо метод для его обработки во время выполнения? –

+0

Я боюсь, что вы должны: - либо обрабатывать его со стороны приложения, которое создает данные, - или передать ваш входной файл через «препроцессор» - ваш код, который читает его, и заменяет все двойные апострофы двумя двойными апострофами. Возможно, библиотека предоставляет такую ​​опцию. Иначе ваш исходный файл не является действительный CSV/TSV. Кстати, если бы я ответил на ваш вопрос, и наличие неэксклюзивных двойных апострофов стало основной причиной вашей проблемы, не могли бы вы пометить мой ответ в качестве ответа? :) Благодаря. –

+0

Файлы данных, которые у меня есть, могут иметь такие разногласия, и проблема в том, что размер данных огромен и может доходить до 100 гб данных в одном файле ... поэтому я не могу спроектировать процессор, так как у него закончится память, и я не могу найти способ справиться с этим при чтении –

0

Если вы используете синтаксический анализатор CSV для анализа входа TSV, у вас будет плохое время. Используйте правильный парсер TSV. uniVocity-parsers поставляется с парсером/автором TSV. Вы можете использовать аннотированные java beans, чтобы анализировать ваш файл непосредственно в экземплярах класса.

Примеры:

Этот код анализирует TSV как строки.

TsvParserSettings settings = new TsvParserSettings(); 

// creates a TSV parser 
TsvParser parser = new TsvParser(settings); 

// parses all rows in one go. 
List<String[]> allRows = parser.parseAll(new FileReader(yourFile)); 

Используйте BeanListProcessor разбора в Java Beans:

BeanListProcessor<TestBean> rowProcessor = new BeanListProcessor<TestBean>(TestBean.class); 

TsvParserSettings parserSettings = new TsvParserSettings(); 
parserSettings.setRowProcessor(rowProcessor); 

TsvParser parser = new TsvParser(parserSettings); 
parser.parse(new FileReader(yourFile)); 

// The BeanListProcessor provides a list of objects extracted from the input. 
List<TestBean> beans = rowProcessor.getBeans(); 

Это как TestBean класс выглядит следующим образом: класса TestBean {

// if the value parsed in the quantity column is "?" or "-", it will be replaced by null. 
@NullString(nulls = { "?", "-" }) 
// if a value resolves to null, it will be converted to the String "0". 
@Parsed(defaultNullRead = "0") 
private Integer quantity; 


@Trim 
@LowerCase 
@Parsed(index = 4) 
private String comments; 

// you can also explicitly give the name of a column in the file. 
@Parsed(field = "amount") 
private BigDecimal amount; 

@Trim 
@LowerCase 
// values "no", "n" and "null" will be converted to false; values "yes" and "y" will be converted to true 
@BooleanString(falseStrings = { "no", "n", "null" }, trueStrings = { "yes", "y" }) 
@Parsed 
private Boolean pending; 

Раскрытие информации: Я являюсь автором этого библиотека. Это бесплатно и бесплатно (лицензия Apache V2.0).

Смежные вопросы