Reading CSV files

This page contains some examples of reading CSV files using Super CSV. You can view the full source of the examples here. For examples of reading CSV files with Dozer (using CsvDozerBeanReader), click here.

Example CSV file

Here is an example CSV file. It has a header and 4 rows of data, all with 10 columns. The mailingAddress column contains data that spans multiple lines and the favouriteQuote column contains data with escaped quotes.

customerNo,firstName,lastName,birthDate,mailingAddress,married,numberOfKids,favouriteQuote,email,loyaltyPoints
1,John,Dunbar,13/06/1945,"1600 Amphitheatre Parkway
Mountain View, CA 94043
United States",,,"""May the Force be with you."" - Star Wars",jdunbar@gmail.com,0
2,Bob,Down,25/02/1919,"1601 Willow Rd.
Menlo Park, CA 94025
United States",Y,0,"""Frankly, my dear, I don't give a damn."" - Gone With The Wind",bobdown@hotmail.com,123456
3,Alice,Wunderland,08/08/1985,"One Microsoft Way
Redmond, WA 98052-6399
United States",Y,0,"""Play it, Sam. Play ""As Time Goes By."""" - Casablanca",throughthelookingglass@yahoo.com,2255887799
4,Bill,Jobs,10/07/1973,"2701 San Tomas Expressway
Santa Clara, CA 95050
United States",Y,3,"""You've got to ask yourself one question: ""Do I feel lucky?"" Well, do ya, punk?"" - Dirty Harry",billy34@hotmail.com,36

Example cell processor configuration

All of the examples on this page use the following cell processor configuration.

It demonstrates:

  • mandatory columns (new NotNull())
  • optional columns (new Optional()), with further processing
  • conversion to Date (new ParseDate()), Boolean (new ParseBool()) and Integer (new ParseInt()) types
  • constraint validation against regular expressions (new StrRegEx()), numeric ranges (new LMinMax()) and uniqueness (new UniqueHashCode())

Don't forget that you can write your own cell processors if you want!

/**
 * Sets up the processors used for the examples. There are 10 CSV columns, so 10 processors are defined. Empty
 * columns are read as null (hence the NotNull() for mandatory columns).
 * 
 * @return the cell processors
 */
private static CellProcessor[] getProcessors() {
        
        final String emailRegex = "[a-z0-9\\._]+@[a-z0-9\\.]+"; // just an example, not very robust!
        StrRegEx.registerMessage(emailRegex, "must be a valid email address");
        
        final CellProcessor[] processors = new CellProcessor[] { 
                new UniqueHashCode(), // customerNo (must be unique)
                new NotNull(), // firstName
                new NotNull(), // lastName
                new ParseDate("dd/MM/yyyy"), // birthDate
                new NotNull(), // mailingAddress
                new Optional(new ParseBool()), // married
                new Optional(new ParseInt()), // numberOfKids
                new NotNull(), // favouriteQuote
                new StrRegEx(emailRegex), // email
                new LMinMax(0L, LMinMax.MAX_LONG) // loyaltyPoints
        };
        
        return processors;
}

Reading with CsvBeanReader

CsvBeanReader is the easiest reader to work with. The example reads each row from the example CSV file into a CustomerBean (which extends from PersonBean).

This relies on the fact that the column names in the header of the CSV file

customerNo,firstName,lastName,birthDate,mailingAddress,married,numberOfKids,favouriteQuote,email,loyaltyPoints

match up exactly with the bean's field names, and the bean has the appropriate setters defined for each field.

If your header doesn't match (or there is no header), then you can simply define your own name mapping array.

Note that the field types in the bean are compatible with the type returned by the cell processors (e.g. birthDate is a java.util.Date in the bean, and uses the ParseDate cell processor).

/**
 * An example of reading using CsvBeanReader.
 */
private static void readWithCsvBeanReader() throws Exception {
        
        ICsvBeanReader beanReader = null;
        try {
                beanReader = new CsvBeanReader(new FileReader(CSV_FILENAME), CsvPreference.STANDARD_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();
                
                CustomerBean customer;
                while( (customer = beanReader.read(CustomerBean.class, header, processors)) != null ) {
                        System.out.println(String.format("lineNo=%s, rowNo=%s, customer=%s", beanReader.getLineNumber(),
                                beanReader.getRowNumber(), customer));
                }
                
        }
        finally {
                if( beanReader != null ) {
                        beanReader.close();
                }
        }
}

Output:

lineNo=4, rowNo=2, customer=CustomerBean [customerNo=1, firstName=John, lastName=Dunbar, birthDate=Wed Jun 13 00:00:00 EST 1945, mailingAddress=1600 Amphitheatre Parkway
Mountain View, CA 94043
United States, married=null, numberOfKids=null, favouriteQuote="May the Force be with you." - Star Wars, email=jdunbar@gmail.com, loyaltyPoints=0]
lineNo=7, rowNo=3, customer=CustomerBean [customerNo=2, firstName=Bob, lastName=Down, birthDate=Tue Feb 25 00:00:00 EST 1919, mailingAddress=1601 Willow Rd.
Menlo Park, CA 94025
United States, married=true, numberOfKids=0, favouriteQuote="Frankly, my dear, I don't give a damn." - Gone With The Wind, email=bobdown@hotmail.com, loyaltyPoints=123456]
lineNo=10, rowNo=4, customer=CustomerBean [customerNo=3, firstName=Alice, lastName=Wunderland, birthDate=Thu Aug 08 00:00:00 EST 1985, mailingAddress=One Microsoft Way
Redmond, WA 98052-6399
United States, married=true, numberOfKids=0, favouriteQuote="Play it, Sam. Play "As Time Goes By."" - Casablanca, email=throughthelookingglass@yahoo.com, loyaltyPoints=2255887799]
lineNo=13, rowNo=5, customer=CustomerBean [customerNo=4, firstName=Bill, lastName=Jobs, birthDate=Tue Jul 10 00:00:00 EST 1973, mailingAddress=2701 San Tomas Expressway
Santa Clara, CA 95050
United States, married=true, numberOfKids=3, favouriteQuote="You've got to ask yourself one question: "Do I feel lucky?" Well, do ya, punk?" - Dirty Harry, email=billy34@hotmail.com, loyaltyPoints=36]

Reading with CsvListReader

CsvListReader is the most primitive reader and should only be used if it's not possible to use the other implementations.

On the other hand, it is the only reader that can be used for reading CSV files with an arbitrary number of columns (which is not technically valid CSV, but still happens), and it's a quick and dirty way to read CSV as a List of Strings.

/**
 * An example of reading using CsvListReader.
 */
private static void readWithCsvListReader() throws Exception {
        
        ICsvListReader listReader = null;
        try {
                listReader = new CsvListReader(new FileReader(CSV_FILENAME), CsvPreference.STANDARD_PREFERENCE);
                
                listReader.getHeader(true); // skip the header (can't be used with CsvListReader)
                final CellProcessor[] processors = getProcessors();
                
                List<Object> customerList;
                while( (customerList = listReader.read(processors)) != null ) {
                        System.out.println(String.format("lineNo=%s, rowNo=%s, customerList=%s", listReader.getLineNumber(),
                                listReader.getRowNumber(), customerList));
                }
                
        }
        finally {
                if( listReader != null ) {
                        listReader.close();
                }
        }
}

Output:

lineNo=4, rowNo=2, customerList=[1, John, Dunbar, Wed Jun 13 00:00:00 EST 1945, 1600 Amphitheatre Parkway
Mountain View, CA 94043
United States, null, null, "May the Force be with you." - Star Wars, jdunbar@gmail.com, 0]
lineNo=7, rowNo=3, customerList=[2, Bob, Down, Tue Feb 25 00:00:00 EST 1919, 1601 Willow Rd.
Menlo Park, CA 94025
United States, true, 0, "Frankly, my dear, I don't give a damn." - Gone With The Wind, bobdown@hotmail.com, 123456]
lineNo=10, rowNo=4, customerList=[3, Alice, Wunderland, Thu Aug 08 00:00:00 EST 1985, One Microsoft Way
Redmond, WA 98052-6399
United States, true, 0, "Play it, Sam. Play "As Time Goes By."" - Casablanca, throughthelookingglass@yahoo.com, 2255887799]
lineNo=13, rowNo=5, customerList=[4, Bill, Jobs, Tue Jul 10 00:00:00 EST 1973, 2701 San Tomas Expressway
Santa Clara, CA 95050
United States, true, 3, "You've got to ask yourself one question: "Do I feel lucky?" Well, do ya, punk?" - Dirty Harry, billy34@hotmail.com, 36]

Reading with CsvMapReader

CsvMapReader is a good compromise if you can't use CsvBeanReader. It allows you to retrieve each column by name from the resulting Map, though you'll have to cast each column to it's appropriate type.

/**
 * An example of reading using CsvMapReader.
 */
private static void readWithCsvMapReader() throws Exception {
        
        ICsvMapReader mapReader = null;
        try {
                mapReader = new CsvMapReader(new FileReader(CSV_FILENAME), CsvPreference.STANDARD_PREFERENCE);
                
                // the header columns are used as the keys to the Map
                final String[] header = mapReader.getHeader(true);
                final CellProcessor[] processors = getProcessors();
                
                Map<String, Object> customerMap;
                while( (customerMap = mapReader.read(header, processors)) != null ) {
                        System.out.println(String.format("lineNo=%s, rowNo=%s, customerMap=%s", mapReader.getLineNumber(),
                                mapReader.getRowNumber(), customerMap));
                }
                
        }
        finally {
                if( mapReader != null ) {
                        mapReader.close();
                }
        }
}

Output:

lineNo=4, rowNo=2, customerMap={loyaltyPoints=0, lastName=Dunbar, numberOfKids=null, married=null, email=jdunbar@gmail.com, customerNo=1, birthDate=Wed Jun 13 00:00:00 EST 1945, firstName=John, mailingAddress=1600 Amphitheatre Parkway
Mountain View, CA 94043
United States, favouriteQuote="May the Force be with you." - Star Wars}
lineNo=7, rowNo=3, customerMap={loyaltyPoints=123456, lastName=Down, numberOfKids=0, married=true, email=bobdown@hotmail.com, customerNo=2, birthDate=Tue Feb 25 00:00:00 EST 1919, firstName=Bob, mailingAddress=1601 Willow Rd.
Menlo Park, CA 94025
United States, favouriteQuote="Frankly, my dear, I don't give a damn." - Gone With The Wind}
lineNo=10, rowNo=4, customerMap={loyaltyPoints=2255887799, lastName=Wunderland, numberOfKids=0, married=true, email=throughthelookingglass@yahoo.com, customerNo=3, birthDate=Thu Aug 08 00:00:00 EST 1985, firstName=Alice, mailingAddress=One Microsoft Way
Redmond, WA 98052-6399
United States, favouriteQuote="Play it, Sam. Play "As Time Goes By."" - Casablanca}
lineNo=13, rowNo=5, customerMap={loyaltyPoints=36, lastName=Jobs, numberOfKids=3, married=true, email=billy34@hotmail.com, customerNo=4, birthDate=Tue Jul 10 00:00:00 EST 1973, firstName=Bill, mailingAddress=2701 San Tomas Expressway
Santa Clara, CA 95050
United States, favouriteQuote="You've got to ask yourself one question: "Do I feel lucky?" Well, do ya, punk?" - Dirty Harry}