嗯,我的原始答案绝对使事情过于复杂...
我们需要为格式取一个String
,并使用一个CVarArgType...
的参数列表(在函数内被视为[CVarArgType]
)。我试图使用Objective-C的NSString
来使它变得复杂。如果我们坚持使用Swift的String
,它实际上有一个接受我们传递的参数的初始化器。
在Swift中编写此函数的最简单方法如下:
func foo(format: String, args: CVarArgType...) {
println(String(format: format, arguments: args))
}
据我所知,Swift不允许使用#define宏。但是,我们可以将该C宏转换为常规的Swift函数。
func foo(format: String, args: CVarArgType...) {
println(NSString(format: format, arguments: getVaList(args)))
}
CVarArgType
是一个 Swift 协议,它接受我们通常传递给字符串格式字符串的类型。
...
使函数接受任意数量的参数作为最后一个参数。在函数内部,这将具有类型 [CVarArgType]
(一个数组)。
与此同时,NSString
的初始化器(以及类似的 NSLog
和其他类似位置)正在寻找一个 CVaListPointer
作为最后一个参数,因此我们可以使用 Swift 的内置函数 getVaList
,将 [CVarArgType]
转换为 CVaListPointer
。
可以这样调用此函数:
foo("%@, %@... %i", "hello", "world", 123)
这将打印:
hello, world... 123
正如@AirspeedVelocity所指出的,通常建议使用withVaList
而不是getVaList
。我们可以这样做:
func foo(format: String, args: CVarArgType...) {
func buildLogString(argList: CVaListPointer) -> String {
return NSString(format: format, arguments: argList) as String
}
println(withVaList(args, buildLogString))
}
对于超出此特定示例的应用程序,重要的是要注意我们可以使用...
来接受任何类型的参数列表,在函数内部,我们得到该类型的数组。
例如:
func bar(myVariadicListOfStuff: MyStuffClass...) {
for thing in myVariadicListOfStuff {
}
}
#define
宏会使调试变得更加困难,因此在Swift中不允许使用。话虽如此,在Swift中可能仍然有一种方法来接受可变数量的参数。 - nhgrifva_list
的 C 函数吗?(如果是的话:withVaList([1, 1.2]) { vprintf("an int: %d\na float: %f", $0) }
将可行)。还是你在问如何在 Swift 中声明可变参数函数?或者一般而言,你想知道如何在 Swift 中定义宏#define
吗? - Airspeed Velocity#define
宏。不过@nhgrif的回答已经解决了你的问题 :) - Airspeed Velocity