【问题标题】:How to efficiently find a string between two given substrings?如何有效地找到两个给定子字符串之间的字符串?
【发布时间】:2015-07-21 06:49:35
【问题描述】:

我有一个字符串,我知道两个唯一的子字符串,哪个在哪​​个之前。找到介于两者之间的字符串的最有效方法是什么?
现在我正在这样做,效果很好:

middleString = line.split(firstSubstr)[1].split(secondSubstr)[0];

我需要对大量大文件中的每一行都执行此操作,但我觉得这种方式不太优雅。我想知道是否有另一种方法可以更有效、更优雅地做到这一点。
如果这行是懒惰地评估的,我认为代码会非常有效,但我认为这个表达式不是这样。假设以 abc 开头的数百个字符的字符串,"a" 第一个子字符串和 "c" 第二个子字符串,代码看起来在返回 "b" 之前,为整个字符串中的所有 ac
另一种可能性是编写我自己的方法,逐个字符地迭代原始字符串,直到找到第一个子字符串,然后附加所有字符,直到找到第二个;但我认为应该有比这更简单的方法。

【问题讨论】:

  • 您可以为此使用正则表达式
  • 如果您知道b 介于ac 之间,那么只需找到a 并搜索b。在调试/详细模式下检查 b 是否在 c 之前。
  • @Juan,如果你的问题已经得到解答,请考虑accepting的答案,否则,请详细说明还有什么不清楚的地方。
  • @aioobe,我无法运行您的代码,但这是因为一些编码问题(我正在使用 /€ 或 /$ 来检测 € 和 $ 符号),它们可以拆分但既不Pattern 和 indexOf 以这种方式检测到它们,所以我遇到了一些越界错误。我想更改它们以测试您的解决方案并衡量性能,我很快就会这样做,现在您已经提醒我了 :)
  • split 采用正则表达式,因此在此处转义 $ 是有意义的,但在 indexOf 情况下则不行。

标签: java string substring


【解决方案1】:

你可以使用indexOf而不是split来解决这个问题,如下:

String in = "abcdefghij";
String part1 = "cd";
String part2 = "gh";

int i1 = in.indexOf(part1) + part1.length();  // end of first match
int i2 = in.indexOf(part2, i1);               // start of second match

System.out.println(in.substring(i1, i2));     // "ef"

这是使用正则表达式和捕获组的一种解决方案:

Pattern p = Pattern.compile(Pattern.quote(part1)
                         + "(.*?)"
                         + Pattern.quote(part2));

Matcher m = p.matcher(in);

if (m.find()) {
    System.out.println(m.group(1));  // "ef"
}

关于哪一个最快,我想说这取决于各种因素。您使用的是哪个 JRE?是否会一遍又一遍地使用相同的模式(您可以编译一次正则表达式并重用它)吗?由于代码只有几行,我建议您简单地尝试一下,并在必要时进行配置。


请注意您建议的解决方案:

middleString = line.split(firstSubstr)[1].split(secondSubstr)[0];

可能会造成毁灭性的内存占用。请参阅此问答:Java String.split memory leak?

【讨论】:

    猜你喜欢
    • 2014-12-07
    • 1970-01-01
    • 2020-05-28
    • 2013-09-13
    • 1970-01-01
    • 2016-04-20
    相关资源
    最近更新 更多