首页 > 解决方案 > 调用在迭代中创建的数组

问题描述

所以我正在编写一个程序,它将读取一个 csv 文件并将文件的每一行放入一个数组中。我想知道是否可以命名在 while 循环中创建的奇异数组。我也很想知道您是否对如何通过 csv 文件的列分隔行(包含 csv 文件的行)有任何想法。

这是我的代码:

package sample.package;

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;

public class SampleClass {

/**
 * @param args
 */
public static String fileLocation;                                                  //Used to declare the file path

public static void readAndArray(String fileLocation) throws IOException {           //Method to read a file and put each line into an array
    BufferedReader lineRead = new BufferedReader(new FileReader(fileLocation));     //Read the file and be able to parse it into separate lines

        String line = lineRead.readLine();                                          //Put line into variable so it isn't a boolean statement

        while ((line = lineRead.readLine()) !=null) {                               //Make it possible to print out array as BufferedReader is used

            String[] oneLine = new String[] {line};                                 //Put parsed line in new array and parsing that data for individual spots in array
            System.out.println(oneLine[0]);                                         //Print out each oneLine array
        }
        lineRead.close();                                                           //Neatly close BufferedReader and FileReader
}


public static void main(String[] args) throws IOException{

    readAndArray("filePath"); //Initialize method by inputting the file path


    }
}

非常感谢你们!

标签: javaarraysbufferedreaderfilereader

解决方案


首先:欢迎来到stackoverflow!

我假设您的问题与某种教育编程任务有关,如果不是的话:有许多处理 CSV 文件的库(具有读取标题行和按标题/列名称读取行条目等附加功能)。

但是......为什么编写 CSV 解析器应该是一项复杂的任务,我的意思是,它基本上只是用逗号分隔的值,phhh!?

长话短说:有RFC 4180,但不要指望你所有的.csv文件都坚持它。引用维基百科

CSV 文件格式未完全标准化。用逗号分隔字段的基本思想很清楚,但是当字段数据也可能包含逗号甚至嵌入的换行符时,这个想法就会变得复杂。CSV 实现可能不处理此类字段数据,或者它们可能使用引号将字段括起来。引号并不能解决所有问题:某些字段可能需要嵌入引号,因此 CSV 实现可能包含转义字符或转义序列。

在您了解并希望理解所提供的有关兼容性的警告之后,以下代码示例完全忽略它并提供一个快速而肮脏的解决方案(不要在生产中使用它,认真...如何不被解雇 101:使用井经过测试的库,如opencsvApache Commons CSV):

public static void main(String[] args)
{
    Path path = Paths.get("some path"); // TODO Change to path to an CSV file

    try (Stream<String> lines = Files.lines(path))
    {
        List<List<String>> rows = lines
                // Map each line of the file to its fields (String[])
                .map(line -> line.split(","))
                // Map the fields of each line to unmodifiable lists
                .map(fields -> Collections.unmodifiableList(Arrays.asList(fields))
                // Collect the unmodifiable lists in an unmodiable list (listception)
                .collect(Collectors.toUnmodifiableList());

        // Ensure file is not empty.
        if (rows.isEmpty())
        {
            throw new IllegalStateException("empty file");
        }

        // Ensure all lines have the same number of fields.
        int fieldsPerRow = rows.get(0).size();
        if (!rows.stream().allMatch(row -> row.size() == fieldsPerRow))
        {
            throw new IllegalStateException("not all rows have the same number of fields");
        }

        // Assume the file has a header line appearing as the first line.
        System.out.printf("Column names: %s\n", rows.get(0));

        // Read the data rows.
        rows.stream()
                .skip(1) // Skip header line
                .forEach(System.out::println);
    }
    catch (IOException | UncheckedIOException e)
    {
        e.printStackTrace(); // TODO Handle exception
    }
}

此代码假定:

  • 字段用逗号分隔
  • 一行被视为由换行符 ('\n')、回车符 ('\r') 或回车符后紧跟换行符中的任何一个终止(BufferedReader 使用的行为Files.lines()
  • 所有行具有相同数量的字段
  • 第一行是标题行
  • 实现者懒得介意用双引号括起来的字段

又快又脏……违反了 RFC ;)


推荐阅读