如何在Swift中实现可展开为循环调用的Objective-C宏的替代方案
Swift中替代ObjC循环调用宏的最优方案
Swift没有提供C/Objective-C体系中的文本替换式预处理宏,这类重复执行逻辑的需求推荐用原生类型安全的方案实现,不会出现宏替换带来的各类潜在问题,性能也和手动写循环完全一致。
原有宏的作用回顾
你给出的Objective-C宏:
#define CALL_FUNC(classname, times, classfuncWithParamter) \ {\ for (int i = 0; i< times; i++) {\ [classname classfuncWithParamter]\ }\ }
调用示例:
CALL_FUNC(AnClass, 10, setName:@"test" withPhone:12345)
核心作用是按指定次数重复执行对应的方法调用。
最优实现方案1:通用高阶函数(适用所有场景)
直接定义一个通用的重复执行函数,适配所有需要循环调用的场景:
func repeatRun(times: Int, action: () throws -> Void) rethrows { guard times > 0 else { return } for _ in 0..<times { try action() } }
对应原宏的调用写法:
repeatRun(times: 10) { AnClass.setName("test", withPhone: 12345) }
优势:不需要侵入现有类型,参数检查严格,完全规避宏文本替换的各类错误。
最优实现方案2:Int扩展(调用更简洁)
如果需要更短的调用写法,可以给Int加扩展:
extension Int { func times(_ action: () throws -> Void) rethrows { guard self > 0 else { return } for _ in 0..<self { try action() } } }
调用示例:
10.times { AnClass.setName("test", withPhone: 12345) }
优势:调用语法更简洁,适合频繁使用重复执行逻辑的项目。
对比原宏的优势
- 无文本替换缺陷:不会出现宏参数带副作用、参数含逗号导致替换错误的问题
- 类型安全:编译器会自动检查方法参数、类型合法性,编译错误指向明确
- 性能无损耗:编译器优化后生成的二进制代码和手动编写for循环完全一致,没有额外开销
内容的提问来源于stack exchange,提问作者waitianlou
相关产品推荐
相关产品推荐

