简体   繁体   English

使用IndexOf获取带有空格和引号的字符串的子字符串

[英]Get Substring of A String with Spaces and Quotes using IndexOf

I have the following String and would like to extract the contents of rule ie My Rule Description Looks Like This: 我有以下字符串,并希望提取规则的内容,即“我的规则描述”如下所示:

rule "My Rule Description Looks Like This"      
        followed by some white space other characters such as quotes".

When i use the following I get a java.lang.StringIndexOutOfBoundsException: String index out of range: -2: 当我使用以下命令时,我得到java.lang.StringIndexOutOfBoundsException:字符串索引超出范围:-2:

String ruleName = rule.substring(rule.indexOf("rule \"" + 7, rule.indexOf("\""));

and when i use lastIndexOf: 当我使用lastIndexOf时:

String ruleName = rule.substring(rule.indexOf("rule \"" + 7, rule.lastIndexOf("\""));

the code executes OK but the output looks like: 代码执行正常,但输出如下:

My Rule Description Looks Like This"        
        followed by some white space other characters and quotes

Any ideas why the first option throws an exception using indexOf? 任何想法为什么第一个选项使用indexOf引发异常?

For any sort of complex text extraction, you might want to consider using regular expressions. 对于各种复杂的文本提取,您可能需要考虑使用正则表达式。 Here is a short script which can extract the rule, and it avoids nasty string manipulations, which, as you have seen, can be prone to error. 这是一个可以提取规则的简短脚本,它避免了讨厌的字符串操作,如您所见,它很容易出错。

String line = "rule \"My Rule Description Looks Like This\"\n";
line += "followed by some white space other characters such as quotes\".";
String pattern = "rule\\s+\"(.*?)\".*";

Pattern r = Pattern.compile(pattern, Pattern.DOTALL);
Matcher m = r.matcher(line);
if (m.find()) {
   System.out.println("Found a rule: " + m.group(1) );
} else {
   System.out.println("Could not find a rule.");
}

Output: 输出:

My Rule Description Looks Like This

Demo here: 演示在这里:

Rextester 右旋酯

From the documentation : 文档中

public String substring(int beginIndex, int endIndex) 公共字符串子字符串(int beginIndex,int endIndex)

if the beginIndex is negative, or endIndex is larger than the length of this String object, or beginIndex is larger than endIndex. 如果beginIndex为负,或者endIndex大于此String对象的长度,或者beginIndex大于endIndex。

You are calling rule.substring(rule.indexOf("rule \\"" + 7, rule.indexOf("\\"")) . The first parameter gives you the index of the first rule + quote , let's say x , + 7. The second parameter gives you the index of the first quote, which is x + 6 ( x - the number of characters in rule . So you are calling substring (x + 7, x +6) , which falls in the exception case: 您正在调用rule.substring(rule.indexOf("rule \\"" + 7, rule.indexOf("\\"")) 。第一个参数为您提供第一个rule + quote的索引,假设x ,+ 7 。第二个参数为您提供第一个引号的索引,即x + 6x rule的字符数。因此,您正在调用substring (x + 7, x +6) ,在特殊情况下:

first parameter biger than the second. 第一个参数大于第二个。

In you rsecond case, using lastIndexOf , you are getting the second quote, so you don't have this problem. 在第二种情况下,使用lastIndexOf获得第二个引号,因此不会出现此问题。

indexOf returns the index of the first occurrence of the specified String. indexOf返回指定字符串首次出现的索引。

So your first example would try to substring starting from index 7 (0 is the index of where your String is found, and then you add 7), and ending at index 5 (where the first " is found). 因此,您的第一个示例将尝试从索引7(0是找到字符串的位置的索引,然后添加7)开始,再到索引5(在其中找到第一个“”)的子字符串。

The substring(int beginIndex, int endIndex) method has some logic in it where if the begin index subtracted from the end index is < 0 it will throw a StringIndexOutOfBoundsException with the value: substring(int beginIndex, int endIndex)方法具有一些逻辑,其中,如果从结束索引中减去的开始索引小于0,则将抛出StringIndexOutOfBoundsException ,其值为:

int subLen = endIndex - beginIndex;
if (subLen < 0) {
    throw new StringIndexOutOfBoundsException(subLen);
}

Your second example doesn't throw an exception, but because you are using lastIndexOf() it will substring from 7 to the end of the String (where there is a "). 您的第二个示例没有引发异常,但是由于您使用的是lastIndexOf() ,它将从7到String的末尾(其中有一个“)”子字符串。

The best solution would be to use a regex pattern like shown in @Tim Biegeleisen's answer 最好的解决方案是使用正则表达式模式,如@Tim Biegeleisen的答案所示

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM