【问题标题】:How to detect if the input csv file has embedded quotes?如何检测输入的 csv 文件是否有嵌入引号?
【发布时间】:2016-06-21 03:01:55
【问题描述】:

我正在编写一个工具,它接受一个 csv 文件的输入并创建一个新的 csv 文件作为输出,并修改了一些字段。在某些情况下,输入 csv 文件在逗号前后嵌入了引号,例如:“a”、“b”、“c”,而在其他情况下,我直接使用 a、b、c。我遇到的问题是,如果输入的 csv 文件嵌入了引号,那么我希望生成的 csv 文件应该具有相同的嵌入引号。我知道我可以在 CSVWriter 的构造函数中控制此设置,如下所示:

CSVWriter writer = 
    new CSVWriter(new FileWriter(csv), ',', CSVWriter.NO_QUOTE_CHARACTER)

但是如何检测我们有哪种情况呢?我是否应该编写一个计算引号字符数的正则表达式并将其与 的计数进行比较,看看它是否超过两倍?例如 "a","b","c" 有 6 个引号和 2 个逗号。

【问题讨论】:

  • 通常只有带逗号的字符串被引用。例如。 Hello, World 可能会显示为 "Hello, World",但 Hello World 不会。我怀疑你应该控制每个字段的报价。
  • 实际上在我拥有的文件中,要么整行都嵌入了引号,要么根本没有嵌入引号
  • 是每行还是每个文件的问题?另外,你能有一排引号不算嵌入吗?
  • 问题在于每个文件,如果输入 csv 文件的所有行都嵌入了引号,那么我希望输出 csv 文件具有相同的模式,即保留这些嵌入的引号
  • 为什么不使用现有的库,如 opencsv.sourceforge.netcommons.apache.org/proper/commons-csv ?它已经为您处理好了。

标签: java regex file csv


【解决方案1】:

您必须阅读整行以检查它是否是嵌入式引号文件。如果您信任您的输入,那么您只需检查第一行(如果您的第一行是列定义,则检查第二行)。

对于这一行,检查它是否以双引号开始和结束(检查该行的第一个和最后一个字符是否为字符串)。

如果你仍然足够相信你的输入,你可以在这里停下来,或者计算“,”的数量(不仅仅是逗号,quote-comma-quote 结构,我猜没有空格)并将其与您的行数进行比较csv 文件应该有(减一),如果它是一个固定值。

如果不是每行的固定值,您的解决方案应该可以工作,因为无论如何正常情况下,CSV 都不应该有逗号作为内容(就像 OldCurmudgeon 在评论中给出的“Hello, world”示例)。

但话又说回来,这更多地取决于您对 csv 格式良好的信任程度,并且您最好确保在异常输入更进一步之前检测到它们。

【讨论】:

    【解决方案2】:

    您可以尝试uniVocity-parsers 来检测格式:

    CsvParserSettings parserSettings = new CsvParserSettings(); //many options here, check the tutorial.
    parserSettings.detectFormatAutomatically();
    
    CsvParser parser = new CsvParser(parserSettings);
    
    //parse and get the detected format
    List<String[]> parsedRows = parser.parseAll(new File("/path/to/input.csv"));
    CsvFormat detectedFormat = parser.getDetectedFormat();
    
    //now, write using the detected format:
    CsvWriterSettings writerSettings = new CsvWriterSettings();
    writerSettings.setFormat(detectedFormat);
    
    CsvWriter writer = new CsvWriter(new File("/path/to/output.csv"), writerSettings);
    writer.writeStringRowsAndClose(parsedRows);
    

    披露:我是这个库的作者。它是开源和免费的(Apache 2.0 许可证)

    【讨论】:

      猜你喜欢
      • 2023-03-27
      • 2019-03-28
      • 2021-09-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-05-22
      • 1970-01-01
      • 2011-09-17
      相关资源
      最近更新 更多