MST

星途 面试题库

面试题:Objective-C字符串处理与正则表达式结合实现复杂文本提取

假设有一段包含多种格式数据的复杂文本,例如:‘订单号:20230815 - 12345,客户姓名:张三,联系电话:13812345678,地址:北京市朝阳区’,要求使用Objective-C和正则表达式提取出订单号、客户姓名、联系电话和地址,并处理可能出现的格式异常情况,说明如何优化代码以提高处理效率和稳定性。
43.4万 热度难度
编程语言Objective-C

知识考点

AI 面试

面试题答案

一键面试

以下是使用Objective-C和正则表达式提取所需信息并处理格式异常的代码示例,同时包含优化思路:

1. 代码实现

#import <Foundation/Foundation.h>

@interface NSString (Regex)
- (NSArray *)matchesForRegex:(NSString *)regex;
@end

@implementation NSString (Regex)
- (NSArray *)matchesForRegex:(NSString *)regex {
    NSError *error = nil;
    NSRegularExpression *regexObject = [NSRegularExpression regularExpressionWithPattern:regex options:0 error:&error];
    if (!regexObject) {
        NSLog(@"正则表达式错误: %@", error);
        return nil;
    }
    NSArray *matches = [regexObject matchesInString:self options:0 range:NSMakeRange(0, self.length)];
    NSMutableArray *results = [NSMutableArray array];
    for (NSTextCheckingResult *match in matches) {
        [results addObject:[self substringWithRange:match.range]];
    }
    return results;
}
@end

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        NSString *text = @"订单号:20230815 - 12345,客户姓名:张三,联系电话:13812345678,地址:北京市朝阳区";
        
        // 订单号正则表达式
        NSString *orderIdRegex = @"订单号:([^,]*)";
        // 客户姓名正则表达式
        NSString *customerNameRegex = @"客户姓名:([^,]*)";
        // 联系电话正则表达式
        NSString *phoneRegex = @"联系电话:(1[3-9]\\d{9})";
        // 地址正则表达式
        NSString *addressRegex = @"地址:([^,]*)";
        
        NSArray *orderIdMatches = [text matchesForRegex:orderIdRegex];
        NSArray *customerNameMatches = [text matchesForRegex:customerNameRegex];
        NSArray *phoneMatches = [text matchesForRegex:phoneRegex];
        NSArray *addressMatches = [text matchesForRegex:addressRegex];
        
        NSString *orderId = orderIdMatches.count > 0? [orderIdMatches[0] componentsSeparatedByString:@":"].lastObject : @"";
        NSString *customerName = customerNameMatches.count > 0? [customerNameMatches[0] componentsSeparatedByString:@":"].lastObject : @"";
        NSString *phone = phoneMatches.count > 0? [phoneMatches[0] componentsSeparatedByString:@":"].lastObject : @"";
        NSString *address = addressMatches.count > 0? [addressMatches[0] componentsSeparatedByString:@":"].lastObject : @"";
        
        NSLog(@"订单号: %@", orderId);
        NSLog(@"客户姓名: %@", customerName);
        NSLog(@"联系电话: %@", phone);
        NSLog(@"地址: %@", address);
    }
    return 0;
}

2. 处理格式异常情况

  • 正则表达式的容错性
    • 例如在联系电话的正则表达式 1[3-9]\\d{9} 中,严格匹配11位数字且以1开头,确保格式正确。
    • 对于订单号、客户姓名、地址的匹配,通过 ([^,]*) 来匹配到逗号之前的内容,这样即使文本格式稍有变化,只要分隔符是逗号,就能正确匹配。
  • 检查匹配结果
    • 在代码中,每次使用 matchesForRegex: 方法获取匹配结果后,先检查数组是否为空,避免后续操作出现空指针异常。例如 if (orderIdMatches.count > 0) 这样的检查。

3. 优化代码以提高处理效率和稳定性

  • 预编译正则表达式:在实际应用中,如果需要多次使用相同的正则表达式,可以将 NSRegularExpression 对象定义为类的属性或全局变量进行预编译,避免每次都创建新的正则表达式对象,提高效率。
  • 减少字符串操作:代码中通过 componentsSeparatedByString:@":"] 分割字符串获取所需信息,如果频繁进行这样的操作会影响性能。可以考虑在正则表达式中直接捕获所需内容,减少分割操作。例如,对于订单号可以修改正则表达式为 订单号:(\\d{8} - \\d{5}) 直接捕获完整订单号格式,避免后续分割。
  • 错误处理优化:在 matchesForRegex: 方法中,当前只是简单打印正则表达式错误,如果在实际应用中,应该根据不同的错误类型采取不同的处理措施,比如返回特定的错误信息给调用者,而不是简单的日志记录。
  • 性能测试与调优:使用 Instruments 工具来分析代码性能瓶颈,特别是在处理大量复杂文本时,根据分析结果针对性优化,如优化正则表达式的复杂度等。