如何获取csv文件中每个字段的最大长度?

时间:2014-03-11 14:44:17

标签: java csv

我需要找出csv文件中每个字段的最大长度。

例如,在以下cvs文件中,因为 1)var1具有最长的字符串shj,其为3个字符,

2)var2包含最长的字符串asdf - 4个字符

3)var3asddfs - 6个字符

var1,var2,var3
a,asdf,df
aa,,
shj,,asddfs

所以,我需要的结果是数组int [] maxLength = {3,4,6}


到目前为止,我正在使用CSV Reader API。这是我的代码

CSVReader reader = new CSVReader (new FileReader(Looks.fileName));
        int [] maxLength = new int[reader.readNext().length];
        for (int i = 0; i < row.length; i++) {
            maxLength[i] = row[i].trim().length() ;
        }
        while ((row = reader.readNext()) !=null ) {
            for (int i = 0; i < row.length; i++) {
                maxLength[i] = Math.max(maxLength[i] , row[i].trim().length() );
            }
        }
        reader.close(); 

工作正常。但对于一个巨大的文件来说太慢了。我有大约100,000,000行。

有没有有效的方法呢?我能否以某种方式使用setAsciiStream来更有效地估计长度?

2 个答案:

答案 0 :(得分:2)

CSVReader是否已缓冲?如果没有,请用FileReader包裹BufferedReader(并使其成为一个漂亮的大缓冲区大小)。

答案 1 :(得分:1)

你的代码尽可能高效 - 它只读取每个字节一次,并且不会对文件进行任何昂贵的搜索。

FileReader包裹在BufferedReader中可能会提高效果 - 尽管CSVReader内部使用BufferedReader并非不可能。

从磁盘读取100,000,000行的速度存在物理限制。在决定你的CSV阅读器很慢之前,值得对你可以编写的最简单的程序进行基准测试,该程序读取整个文件,看看需要多长时间。

BufferedReader reader = new BufferedReader(new FileReader filename);
char[] buffer = new char[1024**1024*10]; // 10MB; whatever
while(reader.read(buffer,0,buffer.length) >= 0) {
     // nothing
}
reader.close();

更新:假设您正在使用OpenCSV,我确认了我的怀疑。

以下是OpenCsv的来源:http://sourceforge.net/p/opencsv/code/HEAD/tree/trunk/src/au/com/bytecode/opencsv/

CSVReader的构造函数将Reader包裹在BufferedReader中,如果它不是BufferedReader

CSVReader.readNext()只是反复调用BufferedReader.readLine(),并对字符进行一些非常基本的操作。

这是 读取文件的最快方式:从头开始,一直读到结束,使用缓冲区,以便底层磁盘读取的大小与硬件和设备相同司机更喜欢。

在一个大文件上运行上面的程序,你会发现它需要与你的CSV解析程序相同的时间 - 因为即使我没有做任何明显的处理,它也有同样的瓶颈。你的 - 从磁盘读取的速度。

确实cat largefile >/dev/null(UNIX)或type largefile >NUL需要相似的时间。

使用分析器运行您的代码,您会发现它花费更多的时间等待read()(在本机方法中是核心Java的一部分)而不是其他任何地方。

您无法对Java程序执行任何操作来加快速度。您可以通过调整硬件和/或操作系统来加快速度 - 例如调整文件系统参数和驱动程序设置,将文件放在RAMdisk或SSD上,等等。