mat*_*att 2 java regex replace
当谈到正则表达式时,我是一个相对新手,但我开始掌握它.我开始在java中编写一个方法来"链接"一个字符串 - 也就是说,扫描它以获取任何url引用(即"http:// ...")或看起来像web地址的字符串("www.example. COM ...")
所以,例如,如果我有一个看起来像这样的字符串:
My favorite site is http://www.example.com. What is yours?
Run Code Online (Sandbox Code Playgroud)
在通过该方法运行之后,您将获得一个字符串,表示:
My favorite site is <a href="http://www.example.com">http://www.example.com</a>. What is yours?
Run Code Online (Sandbox Code Playgroud)
网上淘了一段时间后,我终于可以不同的表达,帮助我做什么我要找的(一些例子包括网址在实际的URL结束,一些编码URL已经尾随句的部分拼凑锚标签等)
这是我到目前为止:
public static String toLinkifiedString(String s, IAnchorBuilder anchorBuilder)
{
if (IsNullOrEmpty(s))
{
return Empty;
}
String r = "(?<![=\"\"\\/>])(www\\.|(http|https|ftp|news|file)(s)?://)([\\w+?\\.\\w+])+([a-zA-Z0-9\\~\\!\\@\\#\\$\\%\\^\\&\\*\\(\\)_\\-\\=\\+\\\\\\/\\?\\.\\:\\;\\'\\,]*)?([^.|'|# |!])";
Pattern pattern = Pattern.compile(r, Pattern.DOTALL | Pattern.UNIX_LINES | Pattern.CASE_INSENSITIVE);
Matcher matcher = pattern.matcher(s);
if (anchorBuilder != null)
{
return matcher.replaceAll(anchorBuilder.createAnchorFromUrl("$0"));
}
return matcher.replaceAll("<a href=\"$0\">$0</a>"); // group 0 is the whole expression
}
public interface IAnchorBuilder
{
public String createAnchorFromUrl(String url);
}
Run Code Online (Sandbox Code Playgroud)
还有简单的toLinkifiedString版本,它只接受字符串s - 它只调用toLinkifiedString(s,null)
就像我说的那样,这个模式正在捕捉我需要捕获的所有内容,并且replaceAll对于每种情况都很有效,除了链接以www开头.如果匹配以"www"开头而不是像"http"或"ftp"这样的协议,我想有条件地在结果链接前面加上"http://".那是:
MyClass.toLinkifiedString("go to www.example.org")
Run Code Online (Sandbox Code Playgroud)
应该回来
go to <a href="http://www.example.com">www.example.org</a>
Run Code Online (Sandbox Code Playgroud)
匹配组如下:
我想我想要做的是,在伪代码中是这样的:
matcher.replaceAll("<a href="(if protocol = "www", insert "http://" + url - otherwise, insert url">url</a>"
Run Code Online (Sandbox Code Playgroud)
这可能吗?或者我应该只为能够仅从以"http:// ..."开头的链接创建锚点而感到高兴:)
感谢任何人都能提供的帮助
Pet*_*ton 10
对于你的具体问题,肯定会使用Tomalak所说的回调功能.
对于所有这些斜线的问题,以及其他各种奇怪的问题......
这是您当前的Java正则表达式跨行分割:
(?<![=\"\"\\/>])
(www\\.|(http|https|ftp|news|file)(s)?://)
([\\w+?\\.\\w+])+
([a-zA-Z0-9\\~\\!\\@\\#\\$\\%\\^\\&\\*\\(\\)_\\-\\=\\+\\\\\\/\\?\\.\\:\\;\\'\\,]*)?
([^.|'|# |!])
Run Code Online (Sandbox Code Playgroud)
和非Java正则表达式相同(没有Java字符串转义):
(?<![=""\/>])
(www\.|(http|https|ftp|news|file)(s)?://)
([\w+?\.\w+])+
([a-zA-Z0-9\~\!\@\#\$\%\^\&\*\(\)_\-\=\+\\\/\?\.\:\;\'\,]*)?
([^.|'|# |!])
Run Code Online (Sandbox Code Playgroud)
以下是对它有什么问题的描述...... :)
第一行 - 你"在字符类中重复,不需要逃避/
第二行 - 好的,除了我不确定你在使用该(s)?部件之后是什么,因为你在前一组中都有https.
第三行 - 你知道你有一个角色课吗?量词不起作用.你可能想要(\w+?\.\w+)+.(那是(\\w+?\\.\\w+)+在Java字符串中.)
第四行 - 哇,逃脱了多少!! 几乎都是不必要的.这给一去:([a-zA-Z0-9~!@#$%^&*()_\-=+\/?.:;',]*)? (并再次:([a-zA-Z0-9~!@#$%^&*()_\\-=+\\/?.:;',]*)?)
第五行 - 交替在字符类中不做任何事情.如果您确实想要防止管道char出现在那里,那么这样做:[^.'#!]并添加一个|.
将所有这些评论放在一起提供了这个正则表达式:
(?<![="/>])
(www\.|(http|https|ftp|news|file)://)
(\w+?\.\w+)+
([a-zA-Z0-9~!@#$%^&*()_\-=+\/?.:;',]*)?
([^.'# !])
Run Code Online (Sandbox Code Playgroud)
或者,再次,逃避Java:
(?<![=\"/>])
(www\\.|(http|https|ftp|news|file)://)
(\\w+?\\.\\w+)+
([a-zA-Z0-9~!@#$%^&*()_\\-=+\\/?.:;',]*)?
([^.'# !])
Run Code Online (Sandbox Code Playgroud)
注意那是多么简单!
回到一行就可以了:
(?<![="/>])(www\.|(http|https|ftp|news|file)://)(\w+?\.\w+)+([a-zA-Z0-9~!@#$%^&*()_\-=+\/?.:;',]*)?([^.'# !])
Run Code Online (Sandbox Code Playgroud)
要么
(?<![=\"/>])(www\\.|(http|https|ftp|news|file)://)(\\w+?\\.\\w+)+([a-zA-Z0-9~!@#$%^&*()_\\-=+\\/?.:;',]*)?([^.'# !])
Run Code Online (Sandbox Code Playgroud)
但是我坚持使用多线 - 只是(?x)在一开始就是plonk ,这是一个有效的正则表达式,它忽略了空格,你可以使用#s进行评论 - 只要有这个就一直是正则表达式的好东西!