我正在尝试制作一个使用Ruby查找域名的正则表达式,所以我尝试了这个:
(?<=.*/).(?=.*/)
在Rubular上我总是看到此错误消息:Forward slashes must be escaped.
我该如何解决这个问题?
答案 0 :(得分:5)
当您使用//
正则表达式文字时,您需要使用反斜杠/
来转义\/
。如果您希望在正则表达式中使用文字/
,则通常更容易避免使用//
字面值。例如,将%r
字面值与任何不会导致冲突的分隔符一起使用。
%r{/}
顺便说一句,Ruby onigmo正则表达式引擎不允许使用可变长度查看后面,所以你的正则表达式无论如何都会返回错误。
答案 1 :(得分:2)
不要重新发明轮子,特别是那些有效的轮子:
require 'uri'
URI.split('http://user:passwd@www.example.com:81/path/to/index.html?foo=bar#baz')
# => ["http",
# "user:passwd",
# "www.example.com",
# "81",
# nil,
# "/path/to/index.html",
# nil,
# "foo=bar",
# "baz"]
或者:
require 'addressable/uri'
uri = Addressable::URI.parse('http://user:passwd@www.example.com:81/path/to/index.html?foo=bar#baz')
uri.authority # => "user:passwd@www.example.com:81"
uri.fragment # => "baz"
uri.host # => "www.example.com"
uri.password # => "passwd"
uri.path # => "/path/to/index.html"
uri.port # => 81
uri.query # => "foo=bar"
uri.query_values # => {"foo"=>"bar"}
uri.scheme # => "http"
uri.to_hash # => {:scheme=>"http", :user=>"user", :password=>"passwd", :host=>"www.example.com", :port=>81, :path=>"/path/to/index.html", :query=>"foo=bar", :fragment=>"baz"}
uri.user # => "user"
在两者之间,Addressable::URI功能更全面,并且非常密切地遵循规范。 Ruby的内置URI适合轻量级提升。
在他们的代码中扎根,你会发现用于撕开URL的正则表达式;你也会发现它们并不是微不足道的,因为网址可能非常“有趣”,“有趣”意味着你会尖叫并拔出你的头发。有关详细信息,请参阅URI RFC。有关建议的模式,请参阅该文档中的“使用正则表达式解析URI引用”。
...我在代码大战中进行练习,不允许使用require
首先,如果是这样,你为什么要求如何写这个?你应该自己解决这些问题。
那说,试试已经创造的东西。这使用RFC中的模式:
URI_REGEX = %r!^(([^:/?#]+):)?(//([^/?#]*))?([^?#]*)(\?([^#]*))?(#(.*))?!
uri_captures = 'http://user:passwd@www.example.com:81/path/to/index.html?foo=bar#baz'.match(URI_REGEX).captures # !> assigned but unused variable - port
# => ["http:",
# "http",
# "//user:passwd@www.example.com:81",
# "user:passwd@www.example.com:81",
# "/path/to/index.html",
# "?foo=bar",
# "foo=bar",
# "#baz",
# "baz"]
user, passwd, host, port = uri_captures[3].split(/[:@]/)
host # => "www.example.com"
为了进一步方便,这里提供了一个提供命名捕获的简单模式:
URI_REGEX = %r!^((?<scheme>[^:/?#]+):)?(//(?<authority>[^/?#]*))?(?<path>[^?#]*)(\?(?<query>[^#]*))?(?<fragment>#(.*))?!
uri_captures = 'http://user:passwd@www.example.com:81/path/to/index.html?foo=bar#baz'.match(URI_REGEX)
authority_captures = uri_captures['authority'].match(/(?<user>[^:]+)?:?(?<passwd>[^@]+)?@?(?<host>.+)(:(?<port>\d+)?)/)
authority_captures['host']
# => "www.example.com"