Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/313.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/amazon-web-services/13.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 数据中带分号的字符串正则表达式解析_Java_Regex_String - Fatal编程技术网

Java 数据中带分号的字符串正则表达式解析

Java 数据中带分号的字符串正则表达式解析,java,regex,string,Java,Regex,String,如何组合一个正则表达式来拆分用分号分隔条件的fiql字符串(下面的示例)。问题是分号也可以在字符串中 我正在使用字符串拆分,但找不到正确的正则表达式。我在下面尝试过,试图得到==之前的最后一个分号: query.split("(;)[^;]*==) 但它只适用于第一个键值 示例字符串: Key1==value1; key2==val;ue2;key3==value3 目标是数组或列表:key1==value1,key2==val;ue2,键3==值3 这里的问题是值2中的分号导致拆分 有什么

如何组合一个正则表达式来拆分用分号分隔条件的fiql字符串(下面的示例)。问题是分号也可以在字符串中

我正在使用字符串拆分,但找不到正确的正则表达式。我在下面尝试过,试图得到==之前的最后一个分号:

query.split("(;)[^;]*==)
但它只适用于第一个键值

示例字符串:

Key1==value1; key2==val;ue2;key3==value3
目标是数组或列表:
key1==value1,key2==val;ue2,键3==值3
这里的问题是值2中的分号导致拆分


有什么想法吗?

看起来你想在
上拆分仅当其后面有
=
,但也没有
在它和那个
==
之间

你快到了。您的代码应该如下所示

split(";(?=[^;]*==)")
请注意,
(?=…)
部分是,它只是检查
之后是否有
存在可由子表达式匹配的部分,但不包括最终匹配中的该部分,因此拆分后它不会消失(它是匹配的)

演示:

输出:

Key1==value1
 key2==val;ue2
key3==value3

如果您还想在
key2
之前去掉空格,则将其作为要拆分的分隔符的一部分。因此,让正则表达式不仅匹配
但它周围还有空格。零个或多个空白可以用
\s*
表示,因此您的代码看起来像

split("\\s*;\\s*(?=[^;]*==)")

改为使用组。并在循环中使用
java.util.regex.Matcher
搜索令牌:

Pattern patrn = Pattern.compile("(?>(\\w+==[\\w;]+)(?:;\\s*|$))");
Matcher mtchr = patrn.matcher("Key1==value1; key2==val;ue2;key3==value3");


while(mtchr.find()) {
    System.out.println(mtchr.group(1));
}

Yields:
Key1==value1
key2==val;ue2
key3==value3
添加;?不幸的是,这将无法工作,因为您的中间令牌将不再终止。

RegExp是邪恶的

如果您可以请求对要分析的字符串进行最小的更改,那么值将被双qoutes包围,那么字符串可以像
Key1==“value1”;键2==“val;ue2”;key3==“value3”
那么这篇文章将对你有所帮助 检查

或者,您需要编写一个自定义字符串解析器。下面是一个快速的非优化


希望这有帮助。

这至少是一个二次正则表达式,因为您要读取两次输入字符串。如果字符串足够长,或者文件足够大,那么速度会非常慢。它是有效的,但是否真的应该使用它?@bashnesnos是的,这种方法可能因为回溯而在性能方面不是最好的,但我不确定它是否是O(N^2)(如果这就是你所说的二次型的意思)。我怀疑它会更接近O(2*N)。此正则表达式将迭代以查找
,然后“向前看”将尝试查找与之匹配的
[^;]*=
,因此
[^;]*
可以将max迭代到下一个
。因此,唯一可以多次迭代的字符区域是那些由
[^;]*
匹配的字符。但它们仍然最多只能迭代2次:当我们搜索分隔符
时迭代一次“…”
,而不是
“…”
保留给
char
类型文本,(2)在非捕获组
(?:regex)
中包装整个正则表达式没有意义,您可以简单地使用
regex
@Pshemo谢谢,我从groovy控制台复制粘贴了它:-)我使用了非捕获组来避免回溯,但我同意,在当前情况下,这更像是一种预先警告。不客气。顺便说一句,
\w
已经包含
0-9
范围,因此您可以跳过正则表达式中的
\d
。此外,您没有义务在回答中添加
EDIT:change description
。如果您看到有可能的改进或问题,请在您的答案中进行更正:)@Pshemo-yup,在更正建议时发现了\d(2):-)我已将全局非捕获组替换为全局原子组,我想现在更有意义了。好吧,这并不是试图在此处使用正则表达式解析任意XHTML:-)为什么不。如果不是性能关键型正则表达式应该在这里发挥作用的话,我绝对同意。无论如何,代码片段应该更快:)
Pattern patrn = Pattern.compile("(?>(\\w+==[\\w;]+)(?:;\\s*|$))");
Matcher mtchr = patrn.matcher("Key1==value1; key2==val;ue2;key3==value3");


while(mtchr.find()) {
    System.out.println(mtchr.group(1));
}

Yields:
Key1==value1
key2==val;ue2
key3==value3