来自URL的Youtube视频ID - 目标C.

The*_*Man 21 iphone cocoa-touch objective-c ios

我基本上有一个Youtube网址作为NSString,但我需要提取网址中显示的视频ID.我在php或其他基于Web的编程语言中找到了很多关于如何做到这一点的教程,但在目标c中没有...

我基本上寻找一个方法,要求NSString url作为参数,并将视频ID作为另一个nsstring返回...

任何人都知道如何做到这一点或任何教程?

Ale*_*lex 68

这是RegExp,它涵盖了这些案例

目标C.

- (NSString *)extractYoutubeIdFromLink:(NSString *)link {
    NSString *regexString = @"((?<=(v|V)/)|(?<=be/)|(?<=(\\?|\\&)v=)|(?<=embed/))([\\w-]++)";
    NSRegularExpression *regExp = [NSRegularExpression regularExpressionWithPattern:regexString
                                                                            options:NSRegularExpressionCaseInsensitive
                                                                              error:nil];

    NSArray *array = [regExp matchesInString:link options:0 range:NSMakeRange(0,link.length)];
    if (array.count > 0) {
        NSTextCheckingResult *result = array.firstObject;
        return [link substringWithRange:result.range];
    }
    return nil;
}
Run Code Online (Sandbox Code Playgroud)

迅速

func extractYoutubeIdFromLink(link: String) -> String? {
    let pattern = "((?<=(v|V)/)|(?<=be/)|(?<=(\\?|\\&)v=)|(?<=embed/))([\\w-]++)"
    guard let regExp = try? NSRegularExpression(pattern: pattern, options: .CaseInsensitive) else {
        return nil
    }
    let nsLink = link as NSString
    let options = NSMatchingOptions(rawValue: 0)
    let range = NSRange(location: 0,length: nsLink.length)
    let matches = regExp.matchesInString(link as String, options:options, range:range)
    if let firstMatch = matches.first {
        return nsLink.substringWithRange(firstMatch.range)
    }
    return nil
}
Run Code Online (Sandbox Code Playgroud)

斯威夫特3

func extractYoutubeIdFromLink(link: String) -> String? {
    let pattern = "((?<=(v|V)/)|(?<=be/)|(?<=(\\?|\\&)v=)|(?<=embed/))([\\w-]++)"
    guard let regExp = try? NSRegularExpression(pattern: pattern, options: .caseInsensitive) else {
        return nil
    }
    let nsLink = link as NSString
    let options = NSRegularExpression.MatchingOptions(rawValue: 0)
    let range = NSRange(location: 0, length: nsLink.length)
    let matches = regExp.matches(in: link as String, options:options, range:range)
    if let firstMatch = matches.first {
        return nsLink.substring(with: firstMatch.range)
    }
    return nil
}
Run Code Online (Sandbox Code Playgroud)


jt_*_*_uk 38

对不起 - 我没有足够的代表为所选答案添加评论.

花了很多年后试图找到正则表达式的正确语法,我遇到了这对我有帮助.希望它可以帮助别人!

NSString *regexString = @"(?<=v(=|/))([-a-zA-Z0-9_]+)|(?<=youtu.be/)([-a-zA-Z0-9_]+)";
Run Code Online (Sandbox Code Playgroud)

取自这里.这适用于以下URL格式:

  • 这对我有用,只是提到你可以访问0号范围来获取它:NSRange videoIDRange = [match rangeAtIndex:0]; NSString*videoID = [message substringWithRange:videoIDRange]; (3认同)

ric*_*ter 15

因此,YouTube网址如下所示:

http://www.youtube.com/watch?v=oHg5SJYRHA0

您感兴趣的视频ID是最后的部分(oHg5SJYRHA0)....虽然它不一定在最后,因为YouTube网址可以在查询字符串中包含其他参数.

你最好的选择可能是使用正则表达式和Foundation的NSRegularExpression课程.我认为这种方法在你发现的其他语言教程中使用 - 注意正则表达式的内容在包含它们的任何语言或工具包中几乎相同,因此在这些教程中找到的任何正则表达式都应该有效为了你.(我建议不要使用你的方法来打破v=11个字符,因为这很容易出现各种失败模式,而正则表达式更强大.)

要查找视频ID,您可能需要正则表达式v=([^&]+).在v=得到我们的查询网址(如果我们得到类似的右边部分watch?fmt=22&v=oHg5SJYRHA0).括号组成一个捕获组,因此我们只能提取视频ID而不是我们用来找到它的其他匹配字符,并且在括号内我们查找一个或多个不是符号的字符序列 - 这样可以确保我们得到了该v=whatever领域的所有内容,如果你得到一个像这样的网址,那么它就没有了watch?v=oHg5SJYRHA0&rel=0.

无论您使用此还是其他正则表达式,您可能都会使用捕获组.(如果没有,rangeOfFirstMatchInString:options:range:就像Dima的答案中所见,就是你所需要的一切.)你可以NSTextCheckingResult使用firstMatchInString:options:range:或类似的方法获取捕获组(作为对象)的内容:

NSError *error = NULL;
NSRegularExpression *regex = 
[NSRegularExpression regularExpressionWithPattern:@"?.*v=([^&]+)"
                                          options:NSRegularExpressionCaseInsensitive
                                            error:&error];
NSTextCheckingResult *match = [regex firstMatchInString:youtubeURL
                                                options:0
                                                  range:NSMakeRange(0, [youtubeURL length])];
if (match) {
    NSRange videoIDRange = [match rangeAtIndex:1];
    NSString *substringForFirstMatch = [youtubeURL substringWithRange:videoIDRange];
}
Run Code Online (Sandbox Code Playgroud)

  • 不是正则表达式有点矫枉过正**并且**对此同时不够灵活吗?我觉得这一切都很糟糕.* (2认同)

Dim*_*ima 9

您可能看到的教程只是有关如何使用正则表达式的说明,这也是您在这种情况下要使用的内容.

您需要使用的Cocoa类是NSRegularExpression.

你的实际正则表达式字符串将取决于你期望url的格式,因为它看起来像youtube有几个.一般功能看起来像:

+ (NSString *)extractYoutubeID:(NSString *)youtubeURL
{
  NSError *error = NULL;  
  NSRegularExpression *regex = [NSRegularExpression regularExpressionWithPattern:@"your regex string goes here" options:NSRegularExpressionCaseInsensitive error:&error];
  NSRange rangeOfFirstMatch = [regex rangeOfFirstMatchInString:youtubeURL options:0 range:NSMakeRange(0, [youtubeURL length])];
  if(!NSEqualRanges(rangeOfFirstMatch, NSMakeRange(NSNotFound, 0)))
  {
    NSString *substringForFirstMatch = [youtubeURL substringWithRange:rangeOfFirstMatch];

    return substringForFirstMatch;
  }
  return nil;
}
Run Code Online (Sandbox Code Playgroud)


小智 7

你甚至不需要正则表达式.无论视频ID的长度及其在URL中的位置如何,以下情况均适用:

NSString *vID = nil;
NSString *url = @"http://www.youtube.com/watch?v=cAcqdjLCN7s";

NSString *query = [url componentsSeparatedByString:@"?"][1];
NSArray *pairs = [query componentsSeparatedByString:@"&"];
for (NSString *pair in pairs) {
    NSArray *kv = [pair componentsSeparatedByString:@"="];
    if ([kv[0] isEqualToString:@"v"]) {
        vID = kv[1];
        break;
    }
}

NSLog(@"%@", vID);
Run Code Online (Sandbox Code Playgroud)