如何在 C# 中使用正则表达式从字符串中提取域名?
Posted
技术标签:
【中文标题】如何在 C# 中使用正则表达式从字符串中提取域名?【英文标题】:How to Extract Domain name from string with Regex in C#? 【发布时间】:2021-09-16 04:59:36 【问题描述】:我想用正则表达式从字符串中提取***域名和国家***域名。我测试了许多像这样的代码的正则表达式:
var linkParser = new Regex(@"\b(?:https?://|www\.)\S+\b", RegexOptions.Compiled | RegexOptions.IgnoreCase);
Match m = linkParser.Match(Url);
Console.WriteLine(m.Value);
但是这些代码都不能正确地做到这一点。 用户输入的文本字符串可以是以下语句:
jonasjohn.com
http://www.jonasjohn.de/snippets/csharp/
jonasjohn.de
www.jonasjohn.de/snippets/csharp/
http://www.answers.com/article/1194427/8-habits-of-extraordinarily-likeable-people
http://www.apple.com
https://www.cnn.com.au
http://www.downloads.news.com.au
https://ftp.android.co.nz
http://global.news.ca
https://www.apple.com/
https://ftp.android.co.nz/
http://global.news.ca/
https://www.apple.com/
https://johnsmith.eu
ftp://johnsmith.eu
johnsmith.gov.ae
johnsmith.eu
www.jonasjohn.de
www.jonasjohn.ac.ir/snippets/csharp
http://www.jonasjohn.de/
ftp://www.jonasjohn.de/
https://subdomain.abc.def.jonasjohn.de/test.htm
我测试的正则表达式:
^(?:https?:\/\/)?(?:[^@\/\n]+@)?(?:www\.)?([^:\/\n]+)"
\b(?:https?://|www\.)\S+\b
://(?<host>([a-z\\d][-a-z\\d]*[a-z\\d]\\.)*[a-z][-a-z\\d]+[a-z])
还有太多 我只需要域名,不需要协议或子域。 喜欢: Domainname.gTLD 或 DomainName.ccTLD 或 DomainName.xyz.ccTLD
我从PUBLIC SUFFIX得到了他们的名单
当然,我在 ***.com 上看过很多帖子,但没有一个回复我。
【问题讨论】:
如果你有Uri,为什么还要使用正则表达式? this回答解决了吗? 试试\b(?:(https?:\/\/|www\.)?)\S+\b
@LeiYang 您是否根据 OP 的可能输入示例列表检查了这一点?
@Fildor 我在一些在线测试仪中试过,你认为哪一行不匹配?
【参考方案1】:
您不需要正则表达式来解析 URL。如果你有一个有效的 URL,你可以使用 Uri 构造函数之一或Uri.TryCreate 来解析它:
if(Uri.TryCreate("http://google.com/asdfs",UriKind.RelativeOrAbsolute,out var uri))
Console.WriteLine(uri.Host);
www.jonasjohn.de/snippets/csharp/
和 jonasjohn.de/snippets/csharp/
虽然不是有效的 URL。 TryCreate
仍然可以将它们解析为相对 URL,但读取 Host
会抛出 System.InvalidOperationException: This operation is not supported for a relative URI.
在这种情况下,您可以使用UriBuilder 类来解析和修改 URL,例如:
var bld=new UriBuilder("jonasjohn.com");
Console.WriteLine(bld.Host);
打印出来
jonasjohn.com
设置 Scheme
属性会生成一个有效的完整 URL:
bld.Scheme="https";
Console.WriteLine(bld.Uri);
这会产生:
https://jonasjohn.com:80/
【讨论】:
听起来不错,但是如果您输入“jonasjohn.com”之类的错误,则会出现一个问题:相对 URI 不支持此操作。 @Feri 使用什么代码?UriBuilder
有效。至于 Uri,我已经解释过这不起作用,因为......为什么假设这是一个域而不是相对 Url 的第五部分? jonasjohn.com
不是有效 URL,但它是 有效 相对 URL。 http://mysite/jonasjohn.com
是一个有效的 URL。 http://mysite
也是如此【参考方案2】:
根据Lidqy的回答,我写了这个函数,我认为支持大部分可能的情况,如果输入的值不在这个范围内,可以让它异常。
public static string ExtractDomainName(string Url)
var regex = new Regex(@"^((https?|ftp)://)?(www\.)?(?<domain>[^/]+)(/|$)");
Match match = regex.Match(Url);
if (match.Success)
string domain = match.Groups["domain"].Value;
int freq = domain.Where(x => (x == '.')).Count();
while (freq > 2)
if (freq > 2)
var domainSplited = domain.Split('.', 2);
domain = domainSplited[1];
freq = domain.Where(x => (x == '.')).Count();
return domain;
else
return String.Empty;
【讨论】:
【参考方案3】:var rx = new Regex(@"^((https?|ftp)://)?(www\.)?(?<domain>[^/]+)(/|$)");
var data = new[] "jonasjohn.com",
"http://www.jonasjohn.de/snippets/csharp/",
"jonasjohn.de",
"www.jonasjohn.de/snippets/csharp/",
"http://www.answers.com/article/1194427/8-habits-of-extraordinarily-likeable-people",
"http://www.apple.com",
"https://www.cnn.com.au",
"http://www.downloads.news.com.au",
"https://ftp.android.co.nz",
"http://global.news.ca",
"https://www.apple.com/",
"https://ftp.android.co.nz/",
"http://global.news.ca/",
"https://www.apple.com/",
"https://johnsmith.eu",
"ftp://johnsmith.eu",
"johnsmith.gov.ae",
"johnsmith.eu",
"www.jonasjohn.de",
"www.jonasjohn.ac.ir/snippets/csharp",
"http://www.jonasjohn.de/",
"ftp://www.jonasjohn.de/",
"https://subdomain.abc.def.jonasjohn.de/test.htm"
;
foreach (var dat in data)
var match = rx.Match(dat);
if (match.Success)
Console.WriteLine("0 => 1", dat, match.Groups["domain"].Value);
else
Console.WriteLine("0 => NO MATCH", dat);
【讨论】:
感谢您回答它在某些方面工作但不能像这样“subdomain.abc.def.jonasjohn.de/test.htm” Afaics 在 .com 或 .co 之后添加 2 个字母的后缀的约定仅限于 .uk、.nz、.au 以及其他一些英联邦域,因此请尝试以下操作:@"^((https?|ftp)://)?(www\.)?[\w\.]*?(?<domain>\w+\.\w+)(\.(uk|au|nz|ir|ae))?(/|$)"
以上是关于如何在 C# 中使用正则表达式从字符串中提取域名?的主要内容,如果未能解决你的问题,请参考以下文章