Puoi consigliare una libreria Java per leggere (e possibilmente scrivere) file CSV? [chiuso]

StackOverflow https://stackoverflow.com/questions/200609

  •  03-07-2019
  •  | 
  •  

Domanda

Puoi consigliare una libreria Java per leggere, analizzare, convalidare e mappare le righe in un file con valori separati da virgola (CSV) su oggetti valore Java (JavaBeans)?

È stato utile?

Soluzione

Abbiamo usato http://opencsv.sourceforge.net/ con buon successo

Ho anche incontrato un'altra domanda con buoni collegamenti: Lib lib o app Java per convertire file CSV in file XML?

Altri suggerimenti

Super CSV è un'ottima scelta per leggere / analizzare, convalidare e mappare i file CSV su POJO!

Noi (il team Super CSV) abbiamo appena rilasciato una nuova versione (puoi download da SourceForge o Maven).

Lettura di un file CSV

L'esempio seguente utilizza CsvDozerBeanReader (un nuovo lettore che abbiamo appena rilasciato che utilizza Dozer per la mappatura dei bean con deep mapping e supporto per la mappatura basata su indice) - si basa sull'esempio del nostro sito Web . Se non hai bisogno della funzionalità Dozer (o vuoi solo una semplice dipendenza autonoma), puoi invece usare CsvBeanReader (vedi esempio di codice ).

Esempio di file CSV

Ecco un esempio di file CSV che rappresenta le risposte a un sondaggio. Ha un'intestazione e 3 righe di dati, tutte con 8 colonne.

age,consentGiven,questionNo1,answer1,questionNo2,answer2,questionNo3,answer3
18,Y,1,Twelve,2,Albert Einstein,3,Big Bang Theory
,Y,1,Thirteen,2,Nikola Tesla,3,Stargate
42,N,1,,2,Carl Sagan,3,Star Wars

Definizione del mapping da CSV a POJO

Ogni riga di CSV verrà letta in un SurveyResponse , ognuno dei quali ha un Elenco di risposta s. Affinché la mappatura funzioni, le tue classi dovrebbero essere Javabeans validi (cioè avere un costruttore no-arg predefinito e avere getter / setter definiti per ogni campo).

In Super CSV definisci la mappatura con un semplice array String: ogni elemento dell'array corrisponde a una colonna nel file CSV.

Con CsvDozerBeanMapper puoi usare:

  • mappature semplici dei campi (ad es. firstName)

  • mappature profonde (ad esempio address.country.code)

  • mapping indicizzato (ad esempio middleNames [1] - indice a base zero per array o raccolte)

  • mappatura profonda + indicizzata (ad es. person.middleNames[1[)

Di seguito è riportata la mappatura dei campi per questo esempio: utilizza una combinazione di questi:

private static final String[] FIELD_MAPPING = new String[] { 
        "age",                   // simple field mapping (like for CsvBeanReader)
        "consentGiven",          // as above
        "answers[0].questionNo", // indexed (first element) + deep mapping
        "answers[0].answer", 
        "answers[1].questionNo", // indexed (second element) + deep mapping
        "answers[1].answer", 
        "answers[2].questionNo", 
        "answers[2].answer" };

Conversione e convalida

Super CSV ha una libreria utile di processori di celle , che può essere utilizzata per convertire le stringhe dal file CSV ad altri tipi di dati (ad es. Data, Numero intero) o per convalidare i vincoli (ad es. obbligatorio / facoltativo, corrispondenza regex, controllo intervallo).

L'uso dei processori di celle è del tutto facoltativo - senza di essi ogni colonna di CSV sarà una stringa, quindi ogni campo deve essere anche una stringa.

La seguente è la configurazione del processore della cella per l'esempio. Come per la mappatura dei campi, ogni elemento dell'array rappresenta una colonna CSV. Dimostra come i processori di celle possono trasformare i dati CSV nel tipo di dati del tuo campo e come possono essere concatenati insieme.

final CellProcessor[] processors = new CellProcessor[] { 
    new Optional(new ParseInt()), // age
    new ParseBool(),              // consent
    new ParseInt(),               // questionNo 1
    new Optional(),               // answer 1
    new ParseInt(),               // questionNo 2
    new Optional(),               // answer 2
    new ParseInt(),               // questionNo 3
    new Optional()                // answer 3
};

Lettura

La lettura con Super CSV è molto flessibile: fornisci il tuo Reader (in modo da poter leggere da un file, il percorso di classe, un file zip, ecc.) e il delimitatore e il carattere di citazione sono configurabili tramite preferenze (di cui esistono diverse configurazioni predefinite che soddisfano la maggior parte degli utilizzi).

Il codice che segue è abbastanza autoesplicativo.

  1. Crea il lettore (con il tuo Reader e le tue preferenze)

  2. (Opzionalmente) leggi l'intestazione

  3. Configura la mappatura del bean

  4. Continua a chiamare read () finché non ottieni un null (fine del file)

  5. Chiudi il lettore

Codice:

ICsvDozerBeanReader beanReader = null;
try {
    beanReader = new CsvDozerBeanReader(new FileReader(CSV_FILENAME),
        CsvPreference.STANDARD_PREFERENCE);

    beanReader.getHeader(true); // ignore the header
    beanReader.configureBeanMapping(SurveyResponse.class, FIELD_MAPPING);

    SurveyResponse surveyResponse;
    while( (surveyResponse = 
        beanReader.read(SurveyResponse.class, processors)) != null ) {
        System.out.println(
            String.format("lineNo=%s, rowNo=%s, surveyResponse=%s",
                beanReader.getLineNumber(), beanReader.getRowNumber(), 
                surveyResponse));
    }

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

Output:

lineNo=2, rowNo=2, surveyResponse=SurveyResponse [age=18, consentGiven=true, answers=[Answer [questionNo=1, answer=Twelve], Answer [questionNo=2, answer=Albert Einstein], Answer [questionNo=3, answer=Big Bang Theory]]]
lineNo=3, rowNo=3, surveyResponse=SurveyResponse [age=null, consentGiven=true, answers=[Answer [questionNo=1, answer=Thirteen], Answer [questionNo=2, answer=Nikola Tesla], Answer [questionNo=3, answer=Stargate]]]
lineNo=4, rowNo=4, surveyResponse=SurveyResponse [age=42, consentGiven=false, answers=[Answer [questionNo=1, answer=null], Answer [questionNo=2, answer=Carl Sagan], Answer [questionNo=3, answer=Star Wars]]]

Ulteriori informazioni

Puoi trovare molte più informazioni sul sito web !

Posso raccomandare SuperCSV . Semplice da usare e ha fatto tutto il necessario.

Ehi, ho un progetto open source per questo: JFileHelpers . Penso che il vantaggio principale sia che utilizza Java Annotations, dai un'occhiata:

Se hai questo bean:

@FixedLengthRecord()
public class Customer {
    @FieldFixedLength(4)
    public Integer custId;

    @FieldAlign(alignMode=AlignMode.Right)
    @FieldFixedLength(20)
    public String name;

    @FieldFixedLength(3)
    public Integer rating;

    @FieldTrim(trimMode=TrimMode.Right)
    @FieldFixedLength(10)
    @FieldConverter(converter = ConverterKind.Date, 
    format = "dd-MM-yyyy")
    public Date addedDate;

    @FieldFixedLength(3)
    @FieldOptional
    public String stockSimbol;    
}

E vuole analizzare questo file:

....|....1....|....2....|....3....|....4                
1   Antonio Pereira     10012-12-1978ABC
2   Felipe Coury          201-01-2007
3   Anderson Polga       4212-11-2007DEF      

Tutto quello che devi fare è questo:

FileHelperEngine<Customer> engine = 
    new FileHelperEngine<Customer>(Customer.class); 
List<Customer> customers = 
    new ArrayList<Customer>();

customers = engine.readResource(
    "/samples/customers-fixed.txt");

Inoltre, supporta la conversione dei dettagli principali, la data e il formato e molto altro. Fammi sapere cosa ne pensi!

Cordiali saluti!

Trovo Flatpack di essere davvero bravo a gestire file CSV stravaganti (escape, citazioni, record errati, ecc.)

La domanda da File CSV a XML posta in precedenza sembra rispondere a tutte le mie domande.

OpenCSV ( http://opencsv.sourceforge.net/ ) si lega anche a JavaBeans usando un Strategia di mappatura della posizione della colonna

  ColumnPositionMappingStrategy strat = new ColumnPositionMappingStrategy();
  strat.setType(YourOrderBean.class);
  String[] columns = new String[] {"name", "orderNumber", "id"}; // the fields to bind do in your JavaBean
  strat.setColumnMapping(columns);

  CsvToBean csv = new CsvToBean();
  List list = csv.parse(strat, yourReader);

Anche JSEFA ( http://jsefa.sourceforge.net ) sembra fare tutto ciò di cui ho bisogno, in particolare associazione a oggetti Java - oltre a supportare FLR e XML

Ho avuto un buon successo sia analizzando che scrivendo file CSV da Java con OpenCSV . Se vuoi leggere o scrivere un foglio di calcolo compatibile con Excel con Java, la libreria POI di Apache è la strada da percorrere .

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top