我需要在iOS应用程序中创建一个伪va_list
来传递给NSString initWithFormat:arguments:
函数,这是我的代码:
NSArray *fixedArguments = [[NSArray alloc] initWithArray:arguments];
NSRange range = NSMakeRange(0, [fixedArguments count]);
va_list fakeArgList = (va_list)malloc(sizeof(NSString *) * [fixedArguments count]);
__unsafe_unretained id *ptr = (__unsafe_unretained id *)fakeArgList;
[fixedArguments getObjects:ptr range:range];
content = [[NSString alloc] initWithFormat:outputFormat
arguments:(va_list)fakeArgList];
free(fakeArgList);
编译器在cast行上显示以下消息:
error: cast of a non-Objective-C pointer type 'va_list' (aka 'char *') to '__unsafe_unretained id *' is disallowed with ARC
getObjects:range:
函数的定义如下:
- (void)getObjects:(id __unsafe_unretained [])objects range:(NSRange)range;
我已经尝试了所有的方法,但仍然不能摆脱这个错误...
有没有办法创建一个启用了ARC的假va_list
?我做错了什么?
发布于 2015-09-25 16:35:59
如果你愿意在你的项目中添加一点swift,这是可能的!
重要的一点是NSArray到[CVarArgType]
的映射,这是va_list
的快速等价物。如果您尝试将[AnyObject]
转换为[CVarArgType]
,则会导致运行时崩溃,但是使用map
,我们可以显式地创建所需的列表。
代码的其余部分是我创建的包装器,这样我就可以从obj-c调用它。您可以为您希望以这种方式调用的任何obj-c函数创建一个包装器。
@objc class StringFormat: NSObject {
class func format(key: String, args: [AnyObject]) -> String {
let locArgs: [CVarArgType] = args.map({ (arg: AnyObject) -> CVarArgType in
if let iArg = (arg is NSNumber ? arg.intValue : nil) {
return iArg
}
return arg as! CVarArgType
});
return String(format: key, arguments: locArgs)
}
}
https://stackoverflow.com/questions/8211996
复制相似问题