Php 如何编写正则表达式从这些URL中提取数字?

Php 如何编写正则表达式从这些URL中提取数字?,php,regex,Php,Regex,我正在尝试编写一个正则表达式来匹配这些URL中的数字(12345678和1234567890) http://www.example.com/p/12345678 http://www.example.com/p/12345678?foo=bar http://www.example.com/p/some-text-123/1234567890?foo=bar 规则: 数字总是在斜杠后面 数字可以是不同的长度 正则表达式必须检查URL中是否有/p/ 这些数字可能在URL的末尾,或者后面可能有

我正在尝试编写一个正则表达式来匹配这些URL中的数字(
12345678
1234567890

http://www.example.com/p/12345678
http://www.example.com/p/12345678?foo=bar
http://www.example.com/p/some-text-123/1234567890?foo=bar
规则:

  • 数字总是在斜杠后面
  • 数字可以是不同的长度
  • 正则表达式必须检查URL中是否有
    /p/
  • 这些数字可能在URL的末尾,或者后面可能有变量
我的尝试:

\/p\/([0-9]+)
与第一个和第二个匹配,但与第三个不匹配。所以我试着:

\/p\/[^\/?]*\/?([0-9]+)
没有快乐


正则表达式可能不是此作业的正确工具。看起来在任何情况下,用URL解析器拆分URL都更有意义。从您的示例来看,数字部分似乎始终是URL路径部分的最后一项。我不确定您使用的是哪种语言,但许多语言都提供了可以将URL解析为其组成部分的函数

$path = parse_url($url, PHP_URL_PATH);
if(strpos($path, "/p/") === 0) {
    $base = basename($path);
} else {
    // error
}

每次都有效,假设$url是您正在解析的字符串。

我扩展了您的版本,现在它适用于所有示例:

\/p\/(.+\/)*(\d+)(\?.+=.+(&.+=.+)*)?$
如果您不关心URL是否有效,可以将正则表达式收缩为:

\/p\/(.+\/)*(\d+)($|\?)
var regex=new regex(@/(\d+);
变量主题=”http://www.example.com/p/some-text-123/1234567890?foo=bar";
var ticket=regex.Match(subject).Groups[“ticket”].Value;

输出:1234567890

如果我理解清楚,您想要的数字只能是:

  • 就在URL的最后一个斜杠之后
  • 不能是变量的一部分,即
    /p/123?foo=bar456
    匹配
    123

    /p/foobar?foo=bar456
    不匹配任何内容
然后可以使用以下正则表达式:

(?=/p/)./\K\d+
解释

(?=/p/)#前瞻:检查URL中的“/p/”
.*/#多亏了贪婪,最后一个“/”
\K#把我们目前所拥有的一切都留在决赛之外
\d+#选择最后一个“/”后面的数字
为了避免转义正斜杠,请不要将其用作:
#(?=/p/)./\K\d+#
就可以了

您可以试试这个。这将根据您的密码捕获整数。请参阅演示。获取捕获或组


您将在(什么编程语言?“\/[^\d]”中使用哪个正则表达式引擎?或者,我相信只要“[^\d]”或“[^\d+]”就行了?@MichaelBerkowski phpy您的第一次尝试确实与第二次尝试(而不是第三次)相匹配@MichaelBerkowski感谢您的帮助-这就是我因阅读过于粗心而得到的结果。:)最后的所有内容都不是必需的,因为这里只有
/p/
\d+
才是重要的。@MichaelBerkowski但是OP提到数字应该是url的最后一部分,后面可能只有参数,所以这确保url有效,只有参数在数字契约之后才是正确的。您可以在它后面加上
($\124;\?)
,因此接下来是查询字符串或字符串的结尾。无需表示
key=value&key=value
@domsteek这也将匹配/sth/psth/sth/1234567890这将匹配不包含
/p/
的url,这是必需的。编辑此项可删除对
解析url
的冗余调用
$path
可以传递给basename,而无需再次调用
parse\u url
var regex = new Regex(@"/(?<ticket>\d+)");

var subject = "http://www.example.com/p/some-text-123/1234567890?foo=bar";

var ticket = regex.Match(subject).Groups["ticket"].Value;
\/p\/(?:.*\/)?(\d+)\b
$re = "/\\/p\\/(?:.*\\/)?(\\d+)\\b/";
$str = "http://www.example.com/p/12345678\nhttp://www.example.com/p/12345678?foo=bar\nhttp://www.example.com/p/some-text-123/1234567890?foo=bar";

preg_match_all($re, $str, $matches);