【问题标题】:Is there a way to process data from a text file containing main headings using a regular expression?有没有办法使用正则表达式处理包含主标题的文本文件中的数据?
【发布时间】:2020-06-18 19:50:22
【问题描述】:

下面是一个sn-p的文本文件格式结构

Historical Sales for: 12th of October  2019, 11:37 am

PRODUCT NAME      QUANTITY
Coke B            5

Historical Sales for: 21st of October  2019, 8:15 pm

PRODUCT NAME      QUANTITY
Peanuts           2

我只想处理列标签和行值,但不包括主标题;在本例中,历史销售额为:2019 年 10 月 12 日上午 11:37

这是我编写的使用正则表达式(\\b)处理文本的代码

        StringBuilder temporary = new StringBuilder();
   
        InputStream inputStream = new FileInputStream(new File(FILE_NAME));            
        BufferedReader readFile = new BufferedReader(new InputStreamReader(inputStream));
        
        String next; 
        
        while ((next = readFile.readLine()) != null) {
           temporary.append(next).append("\n");
        }   

        next = String.format("%13s", ""); // spacing for column headers          
        System.out.println(temporary.toString().replaceAll("(\\b)", next));

【问题讨论】:

  • \\b{3} 在每个单词边界位置匹配一个空字符串 3 次。因此,有效地匹配一个空字符串。 \\b{3} = \\b
  • 您应该为示例文本文件使用预先格式化的文本块(代码块),而不是文本文件的图片。 —— 这是一个包含多个“Historical Sales for:”标题的单个文本文件,还是每个都有一个标题的多个文件?标题的一致性如何?如果标题本身符合模式,也许您可​​以在处理文件时匹配并丢弃标题。
  • for (; <condition> ;)while (<condition>) 相同——while 是一个更自然的构造...... while ( line = readFile.readLine() ) != null) { if (isHeaderLine(line) { continue; } temporaryData.append..... }
  • @Edward 它匹配文件中的整个文本,这不是我想要的。我的目标是完全丢弃标题 Historical Sales for: 和相应的日期与时间
  • 正则表达式\\b 匹配a \ + b。演示->regex101.com/r/XIvBBb/1。同样,据我所知,没有\\b in the Java language

标签: java regex replace file-processing


【解决方案1】:

如果您的意图是只打印这些行:

PRODUCT NAME      QUANTITY
Chips             2
Coke B            5

还有类似的。我建议您使用 Java 8 流并使用下面的正则表达式删除不需要的行:

public static void main(String[] args) throws Exception {
    String collect = Files.lines(Paths.get("file.txt"))
            .filter(line -> !line.matches("^Historical Sales for.*$") && !line.matches("^\\s*$"))
            .map(line -> line+="\n")
            .collect(Collectors.joining());
    System.out.println(collect);
}

这样你就有了:

PRODUCT NAME      QUANTITY
Chips             2
Coke B            5
PRODUCT NAME      QUANTITY
(...)

使用 Streams 的一个优点是 .collect() 方法允许您将字符串直接解析为 List

如果你想保持你的榜样,你可以这样做:

StringBuilder temporaryData = new StringBuilder();

InputStream inputStream = new FileInputStream(new File("file.txt"));
BufferedReader readFile = new BufferedReader(new InputStreamReader(inputStream));

String next;

while ((next = readFile.readLine()) != null) {
    temporaryData.append(next).append("\n");
}

next = String.format("%13s", ""); // spacing for column headers
String formattedString = temporaryData.toString().replaceAll("(\\b{3})", next);
String stringWithoutHeaders = formattedString.replaceAll("^Historical Sales for.*$", "").replaceAll("^\\s*$", "");
System.out.println(stringWithoutHeaders);

【讨论】:

  • 谢谢! Java 8 的方法更具可读性并且成功了 :)
猜你喜欢
  • 2016-04-02
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-03-19
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-07-07
相关资源
最近更新 更多