如何在Objective C(NSRegularExpression)中编写正则expression式?

我有这个正则expression式工作,当我在PHP中testing,但它不能在Objective C中工作:

(?:www\.)?((?!-)[a-zA-Z0-9-]{2,63}(?<!-))\.?((?:[a-zA-Z0-9]{2,})?(?:\.[a-zA-Z0-9]{2,})?) 

我试图逃脱转义字符,但这也没有帮助。 我应该逃避其他angular色吗?

这是我在Objective C中的代码:

 NSMutableString *searchedString = [NSMutableString stringWithString:@"domain-name.tld.tld2"]; NSError* error = nil; NSRegularExpression* regex = [NSRegularExpression regularExpressionWithPattern:@"(?:www\\.)?((?!-)[a-zA-Z0-9-]{2,63}(?<!-))\\.?((?:[a-zA-Z0-9]{2,})?(?:\\.[a-zA-Z0-9]{2,})?)" options:0 error:&error]; NSArray* matches = [regex matchesInString:searchedString options:0 range:NSMakeRange(0, [searchedString length])]; for ( NSTextCheckingResult* match in matches ) { NSString* matchText = [searchedString substringWithRange:[match range]]; NSLog(@"match: %@", matchText); } 

– 更新 –

这个正则expression式在PHP中返回值为“domain-name”和“tld.tld2”的数组,但在Objective C中,我只获得一个值:“domain-name.tld.tld2”

– 更新2 –

这个正则expression式从string中提取“域名”和“TLD”:

  • domain.com =(domain,com)
  • domain.co.uk =(domain,co.uk)
  • -test-domain.co.u =(test-domain,co)
  • -test-domain.co.uk- =(test-domain,co.uk)
  • -test-domain.co.uk =(test-domain,co)
  • -test-domain.co-m =(testing域)
  • -test-domain-.co.uk =(testing域)

它需要有效的域名(不以' – '开头或结尾,长度在2到63个字符之间),如果部分有效,至多两个TLD部分(至less两个字符只包含字母和数字)

希望这个解释有帮助。

一个NSTextCheckingResult有多个项目索引到它。

[match rangeAtIndex:0]; 是完整的比赛。
[match rangeAtIndex:1]; (如果存在)是第一次捕获组匹配。
等等

你可以使用这样的东西:

 NSString *searchedString = @"domain-name.tld.tld2"; NSRange searchedRange = NSMakeRange(0, [searchedString length]); NSString *pattern = @"(?:www\\.)?((?!-)[a-zA-Z0-9-]{2,63}(?<!-))\\.?((?:[a-zA-Z0-9]{2,})?(?:\\.[a-zA-Z0-9]{2,})?)"; NSError *error = nil; NSRegularExpression* regex = [NSRegularExpression regularExpressionWithPattern: pattern options:0 error:&error]; NSArray* matches = [regex matchesInString:searchedString options:0 range: searchedRange]; for (NSTextCheckingResult* match in matches) { NSString* matchText = [searchedString substringWithRange:[match range]]; NSLog(@"match: %@", matchText); NSRange group1 = [match rangeAtIndex:1]; NSRange group2 = [match rangeAtIndex:2]; NSLog(@"group1: %@", [searchedString substringWithRange:group1]); NSLog(@"group2: %@", [searchedString substringWithRange:group2]); } 

NSLog输出:

匹配:domain-name.tld.tld2
域名
tld.tld2

做testing,匹配范围是有效的。

在这种情况下更简单:

 NSString *searchedString = @"domain-name.tld.tld2"; NSRange searchedRange = NSMakeRange(0, [searchedString length]); NSString *pattern = @"(?:www\\.)?((?!-)[a-zA-Z0-9-]{2,63}(?<!-))\\.?((?:[a-zA-Z0-9]{2,})?(?:\\.[a-zA-Z0-9]{2,})?)"; NSError *error = nil; NSRegularExpression* regex = [NSRegularExpression regularExpressionWithPattern:pattern options:0 error:&error]; NSTextCheckingResult *match = [regex firstMatchInString:searchedString options:0 range: searchedRange]; NSLog(@"group1: %@", [searchedString substringWithRange:[match rangeAtIndex:1]]); NSLog(@"group2: %@", [searchedString substringWithRange:[match rangeAtIndex:2]]); 

Swift 3.0:

 let searchedString = "domain-name.tld.tld2" let nsSearchedString = searchedString as NSString let searchedRange = NSMakeRange(0, searchedString.characters.count) let pattern = "(?:www\\.)?((?!-)[a-zA-Z0-9-]{2,63}(?<!-))\\.?((?:[a-zA-Z0-9]{2,})?(?:\\.[a-zA-Z0-9]{2,})?)" do { let regex = try NSRegularExpression(pattern:pattern, options: []) let matches = regex.matches(in:searchedString, options:[], range:searchedRange) for match in matches { let matchText = nsSearchedString.substring(with:match.range); print("match: \(matchText)"); let group1 : NSRange = match.rangeAt(1) let matchText1 = nsSearchedString.substring(with: group1) print("matchText1: \(matchText1)") let group2 = match.rangeAt(2) let matchText2 = nsSearchedString.substring(with: group2) print("matchText2: \(matchText2)") } } catch let error as NSError { print(error.localizedDescription) } 

打印输出:

匹配:domain-name.tld.tld2
matchText1:域名
matchText2:tld.tld2

在这种情况下更简单:

 do { let regex = try NSRegularExpression(pattern:pattern, options: []) let match = regex.firstMatch(in:searchedString, options:[], range:searchedRange) let matchText1 = nsSearchedString.substring(with: match!.rangeAt(1)) print("matchText1: \(matchText1)") let matchText2 = nsSearchedString.substring(with: match!.rangeAt(2)) print("matchText2: \(matchText2)") } catch let error as NSError { print(error.localizedDescription) } 

打印输出:

matchText1:域名
matchText2:tld.tld2

根据苹果公司的文件 ,这些字符必须被引用(使用\)作为字面值:

 * ? + [ ( ) { } ^ $ | \ . / 

如果你能解释你正在努力达成的目标,这也将有所帮助。 你有任何testing夹具?