簡體   English   中英

如何在java中解析一種形式的csv文件

[英]How to parse a form of csv file in java

我試圖通過使用帶分隔符的掃描儀來解析一個相當特殊格式的文件,但我對正則表達式很陌生。 格式:

“瑪麗”、“帕特里夏”、“琳達”、“芭芭拉”、“伊麗莎白”、“珍妮弗”……

目前,我正在使用以下分隔符和代碼:

static void readNames(String[] names) {

    try {
        Scanner sc = new Scanner(new File("names.txt")).useDelimiter(",");
        int count = 0;

        while(sc.hasNext()) {

            names[count] = sc.next();
            count ++;


        }
    } catch (FileNotFoundException e) {

        e.printStackTrace();
    }

} 

但是,這給了我字符串周圍的引號,這不是我想要的。

然后,我嘗試使用以下分隔符:

String delimiter = " "," ";

由於引號的數量,我很快意識到它不被識別為字符串。

這是在我得到答案后進行編輯的,但是有什么方法可以按照我在第二個分隔符中的意圖進行操作,使用“,”作為分隔符?

根據您帖子中給出的數據,我認為您可以使用這種模式“,”|“

以下是您可以編寫的代碼類型,

public static void main(String[] args) throws Exception {
    Scanner sc = new Scanner(new FileInputStream("filename.txt"));
    sc.useDelimiter(Pattern.compile("\",\"|\""));

    while(sc.hasNext()) {
        System.out.println(sc.next());
    }
    sc.close();
}

如果您只想要一個 Java 編寫的有用的 csv 解析器。 我最近寫了一篇很不錯的:

public static Iterable<String[]> parseCSV(final InputStream stream) throws IOException {
    return new Iterable<String[]>() {
        @Override
        public Iterator<String[]> iterator() {
            return new Iterator<String[]>() {
                static final int UNCALCULATED = 0;
                static final int READY = 1;
                static final int FINISHED = 2;
                int state = UNCALCULATED;
                ArrayList<String> value_list = new ArrayList<>();
                StringBuilder sb = new StringBuilder();
                String[] return_value;

                public void end() {
                    end_part();
                    return_value = new String[value_list.size()];
                    value_list.toArray(return_value);
                    value_list.clear();
                }

                public void end_part() {
                    value_list.add(sb.toString());
                    sb.setLength(0);
                }

                public void append(int ch) {
                    sb.append((char) ch);
                }

                public void calculate() throws IOException {
                    boolean inquote = false;
                    while (true) {
                        int ch = stream.read();
                        switch (ch) {
                            default: //regular character.
                                append(ch);
                                break;
                            case -1: //read has reached the end.
                                if ((sb.length() == 0) && (value_list.isEmpty())) {
                                    state = FINISHED;
                                } else {
                                    end();
                                    state = READY;
                                }
                                return;
                            case '\r':
                            case '\n': //end of line.
                                if (inquote) {
                                    append(ch);
                                } else {
                                    end();
                                    state = READY;
                                    return;
                                }
                                break;
                            case ',': //comma
                                if (inquote) {
                                    append(ch);
                                } else {
                                    end_part();
                                    break;
                                }
                                break;
                            case '"': //quote.
                                inquote = !inquote;
                                break;
                        }
                    }
                }

                @Override
                public boolean hasNext() {
                    if (state == UNCALCULATED) {
                        try {
                            calculate();
                        } catch (IOException ex) {
                        }
                    }
                    return state == READY;
                }

                @Override
                public String[] next() {
                    if (state == UNCALCULATED) {
                        try {
                            calculate();
                        } catch (IOException ex) {
                        }
                    }
                    state = UNCALCULATED;
                    return return_value;
                }
            };
        }
    };
}

您通常會非常有幫助地處理此問題,例如:

for (String[] csv : parseCSV(stream)) {
    //<deal with parsed csv data>
}

通常,它將 csv 流解析器包裝在一個可迭代對象中,因此您可以使用特殊的 java for 循環。 所以你給它一個流,它會給你一個字符串數組的 for 循環,這通常是你想要這些數據的最佳方式。

如果你更想理解,你需要用額外的信息更好地表達你的問題,明確你認為你需要什么以及為什么,因為你的大部分帖子沒有多大意義。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM