2016-01-28 47 views
7

Ho un ArrayList<Metadata> e voglio sapere se c'è un'API Java per lavorare con file CSV che ha un metodo di scrittura che accetta un ArrayList <> come parametro simile a LinqToCsv in. Netto. Come so OpenCSV è disponibile ma la classe CsvWriter non accetta una raccolta. mio metadati Class èCome scrivere ArrayList in un file csv

public class Metadata{ 
    private String page; 
    private String document; 
    private String loan; 
    private String type; 
} 
ArrayList<Metadata> record = new ArrayList<Metadata>(); 

una volta Io popolo la cronaca, voglio scrivere ogni riga in un file CSV. Si prega di suggerire.

+0

Perché no. Che mi dici di javacsv? – Satya

risposta

8

Sicuramente ci sarà un mucchio di API che lo farà per voi, ma perché non farlo da soli per un caso così semplice? Ti farà risparmiare una dipendenza, che è una buona cosa per qualsiasi progetto di qualsiasi dimensione.

Creare un metodo toCsvRow() in Metadata che unisce le stringhe separate da una virgola.

public String toCsvRow() { 
    return Stream.of(page, document, loan, type) 
      .map(value -> value.replaceAll("\"", "\"\"")) 
      .map(value -> Stream.of("\"", ",").anyMatch(value::contains) ? "\"" + value + "\"" : value) 
      .collect(Collectors.joining(",")); 
} 

Raccogliere il risultato di questo metodo per ogni oggetto Metadata separato da una nuova riga.

String recordAsCsv = record.stream() 
     .map(Metadata::toCsvRow) 
     .collect(Collectors.joining(System.getProperty("line.separator"))); 

EDIT Se non siete così fortunati da avere Java 8 e l'API flusso a vostra disposizione, questo sarebbe quasi come semplice utilizzando una lista tradizionale.

public String toCsvRow() { 
    String csvRow = ""; 
    for (String value : Arrays.asList(page, document, loan, type)) { 
     String processed = value; 
     if (value.contains("\"") || value.contains(",")) { 
      processed = "\"" + value.replaceAll("\"", "\"\"") + "\""; 
     } 
     csvRow += "," + processed; 
    } 
    return csvRow.substring(1); 
} 
+0

Esso crea un [flusso] (https://docs.oracle.com/javase/8/docs/api/java/util/stream/package-summary.html#package.description) di un numero arbitrario di oggetti del stesso tipo. Gli stream sono una nuova funzionalità di Java 8. – Henrik

+0

ok, sono legato a Java 7, ecco perché non riconosce Stream.of(). c'è un modo per farlo senza streaming i.e su Java 7. – Maverick

+0

Certo, la mappatura e la raccolta di flussi è semplicemente migliore. Vedi risposta aggiornata - dovresti essere in grado di fare da solo l'ultima parte di mettere ogni riga su una linea separata. – Henrik

1

Utilizzando CSVWriter, si potrebbe convertire il ArrayList a un array, e passare che per lo scrittore.

csvWriter.writeNext(record.toArray(new String[record.size()])); 
+0

questo è un java.lang.ArrayStoreException – Maverick

0

Se si dispone di un ArrayList di oggetti (metadati nel tuo caso) si può usare il BeanToCSV al posto del CSVWriter.

Potete guardare il BeanToCSVTest in the opencsv source code per gli esempi di come usarlo.

+0

In genere, le risposte devono stare da soli. Puoi aggiungere una classe di esempio di codice piccolo? L'esempio collegato è di quasi 500 righe. –

+0

mmmmkay - Come circa i testWriteQuotes test() all'interno del BeanToCSVTest che prende il Testdata arrayList e invia il risultato al Writer in dotazione (per il caso di test è uno StringWriter in modo da poter testare il risultato dispiace non mi riferisco a venire. fuori come sprezzante o sarcastico, ma io sono empio occupato e non ho tempo di scrivere esempi. la maggior parte di openCSV ha prove che, mentre ha ammesso nel suo insieme sono troppo per essere utilizzato come esempio, può essere consultato la pagina singolarmente come esempi In futuro cercherò di restringere a prove specifiche che meglio rispondono alla domanda. –