问题

阅读一些教程后,我仍然无法得到它.

有人可以解释?:是如何使用的吗?



解决方法

让我尝试用一​​个例子解释这个.

请考虑以下文字:

http://stackoverflow.com/
http://stackoverflow.com/questions/tagged/regex

现在,如果我在其下面应用正则表达式...

(http|ftp)://([^/\r\n]+)(/[^\r\n]*)?

...我会得到以下结果:

Match "http://stackoverflow.com/"
     Group 1: "http"
     Group 2: "stackoverflow.com"
     Group 3: "/"

Match "http://stackoverflow.com/questions/tagged/regex"
     Group 1: "http"
     Group 2: "stackoverflow.com"
     Group 3: "/questions/tagged/regex"

但我不在乎协议 - 我只想要的主机和URL的路径.所以,我改变正则表达式以包括非捕获组(?:).

(?:http|ftp)://([^/\r\n]+)(/[^\r\n]*)?

现在,我的结果如下所示:

Match "http://stackoverflow.com/"
     Group 1: "stackoverflow.com"
     Group 2: "/"

Match "http://stackoverflow.com/questions/tagged/regex"
     Group 1: "stackoverflow.com"
     Group 2: "/questions/tagged/regex"

看到吗?第一组未被捕获.解析器使用它来匹配文本,但在最后的结果中稍后忽略它.


EDIT:

根据要求,让我尝试解释群体.

好吧,小组服务于许多目的.它们可以帮助您从更大的匹配(也可以命名)中提取精确的信息,他们允许您重新匹配之前匹配的组,并且可以用于替换.让我们尝试一些例子,我们吗?

好的,假设您有某种类型的XML或HTML(请注意 regex可能不是最好的工作,但它是很好的例子).你想解析标签,所以你可以这样做(我已经添加了空格,使其更容易理解):

   \<(?<TAG>.+?)\> [^<]*? \</\k<TAG>\>
or
   \<(.+?)\> [^<]*? \</\1\>

第一个正则表达式有一个命名组(TAG),而第二个正则表达式使用一个公共组.两个正则表达式都做同样的事情:它们使用第一组中的值(标记的名称)来匹配结束标记.不同的是,第一个使用名称来匹配值,第二个使用组索引(从1开始).

现在我们尝试一些替代.考虑以下文本:

Lorem ipsum dolor sit amet consectetuer feugiat fames malesuada pretium egestas.

现在,让我们使用这个蠢的正则表达式:

\b(\S)(\S)(\S)(\S*)\b

此正则表达式匹配至少包含3个字符的字词,并使用组来分隔前三个字母.其结果是:

Match "Lorem"
     Group 1: "L"
     Group 2: "o"
     Group 3: "r"
     Group 4: "em"
Match "ipsum"
     Group 1: "i"
     Group 2: "p"
     Group 3: "s"
     Group 4: "um"
...

Match "consectetuer"
     Group 1: "c"
     Group 2: "o"
     Group 3: "n"
     Group 4: "sectetuer"
...

所以,如果我们应用替换字符串...

$1_$3$2_$4

...在它上面,我们试图使用第一组,添加下划线,使用第三组,然后第二组,添加另一个下划线,然后第四组.结果字符串将如下所示.

L_ro_em i_sp_um d_lo_or s_ti_ a_em_t c_no_sectetuer f_ue_giat f_ma_es m_la_esuada p_er_tium e_eg_stas.

您也可以使用命名组替换,使用 $ {name} .

要使用正则表达式进行游戏,我建议您 http://regex101.com/ ,它提供了大量的关于正则表达式如何工作的细节;它还提供了几个正则表达式引擎可供选择.




相关问题推荐