java是与此字符序列不匹配的正则表达式
这是我的正则表达式,我正在尝试搜索所有特殊字符,这样我就可以避开它们
(\(|\)|\[|\]|\{|\}|\?|\+|\\|\.|\$|\^|\*|\||\!|\&|\-|\@|\#|\%|\_|\"|\:|\<|\>|\/|\;|\'|\`|\~)
我这里的问题是,我不想只在序列中出现某些特殊字符时才对其进行转义
像这样(.*)
Sting message = "Hi, Mr.Xyz! Your account number is :- (1234567890) , (,*) &$@%#*(....))(((";
根据当前的正则表达式逃跑后我得到的是
Hi, Mr\.Xyz\! Your account number is \:\- \(1234567890\) , \(,\*\) \&\$\@\%\#\*\(\.\.\.\.\)\)\(\(\(
但是,我不想逃避这一部分(.*)
我想保持现状
我上面的正则表达式只用于搜索,所以我不想与这个部分匹配(.*)
,我的问题将得到解决
有人能建议正则表达式不转义字符串的这一部分吗
# 1 楼答案
有关如何使用正则表达式执行此操作,请参见@nhahtdh
作为替代方案,这里有一个解决方案不使用正则表达式,而是使用Guava的CharMatcher:
# 2 楼答案
这个答案只是为了证明这种可能性。在生产代码中使用它是有问题的强>
可以使用Java字符串
replaceAll
函数:结果:
另一项测试:
结果:
解释
原始正则表达式:
请注意,当在字符串中指定正则表达式时,
\
将再次转义,并且"
需要转义。上面可以看到字符串中的结果正则表达式原始替换字符串:
由于
$
在替换字符串中有特殊的含义,并且您希望为$2
保留它,因此需要转义\
,以便\
不会转义$
。将替换字符串放在带引号的字符串中,需要将\
的数量加倍,以转义\
在我们解剖怪物之前,让我们先谈谈这个想法。我们将尽可能多地使用非特殊字符和不希望替换的序列。下一个字符要么是不构成我们不想替换的序列的特殊字符,要么是字符串的结尾(这意味着我们已经找到了所有需要替换的字符(如果有)
当然,我们可以将任意字符串看作是由以下许多模式连续组成:
当不使用^ {< CD14>}的正则表达式时,函数p>^ {CD1>}可以找到不连续的匹配,这可以在序列的中间切去不被替换并使其混乱。{[0 or more (non-special character or special pattern not to be replace)][special character]
,字符串以[0 or more (non-special character or special pattern not to be replace)]
结尾\G
:从上次匹配开始((?:[^()\[\]{}?+\\.$^*|!&@#%_":<>/;'`~-]|\Q(.\*)\E)*+)
:捕获0个或多个不被替换的非特殊字符或特殊模式。注意,我在*
之后添加了所有格限定符+
。这将防止引擎在找不到我们在此之后指定的特殊字符时进行回溯[^()\[\]{}?+\\.$^*|!&@#%_":<>/;'`~-]
:特殊字符的否定字符类\Q(.*)\E
:特殊序列(.*)
不被替换,文字由\Q
和\E
引用([()\[\]{}?+\\.$^*|!&@#%_":<>/;'`~-])
:捕获单个特殊字符整个正则表达式将匹配最小长度为1(特殊字符)的字符串。第一个捕获组包含不应更换的部件,第二个捕获组包含应更换的特殊字符