将数组传递给具有可变数量的args的函数。

时间:2022-12-10 23:15:09

In The Swift Programming Language, it says:

在Swift编程语言中,它说:

Functions can also take a variable number of arguments, collecting them into an array.

函数还可以接受可变数量的参数,将它们收集到一个数组中。

  func sumOf(numbers: Int...) -> Int {
      ...
  }

When I call such a function with a comma-separated list of numbers (`sumOf(1, 2, 3, 4), they are made available as an array inside the function.

当我用逗号分隔的数字列表(' sumOf(1,2,3,4)调用这样的函数时,它们可以作为函数中的数组使用。

Question: what if I already have an array of numbers that I want to pass to this function?

问题:如果我已经有了一个要传递给这个函数的数字数组,该怎么办?

let numbers = [1, 2, 3, 4]
sumOf(numbers)

This fails with a compiler error, “Could not find an overload for '__conversion' that accepts the supplied arguments”. Is there a way to turn an existing array into a list of elements that I can pass to a variadic function?

这在编译器错误时失败,“无法找到接受提供参数的‘__conversion’的过载”。是否有一种方法可以将一个现有的数组转换成一个元素列表,并将其传递给一个变量函数?

6 个解决方案

#1


79  

Splatting is not in the language yet, as confirmed by the devs. Workaround for now is to use an overload or wait if you cannot add overloads.

正如开发人员所证实的,溅射还没有出现在语言中。目前的解决方案是使用重载,如果不能添加重载,则等待。

#2


55  

Here's a work around that I found. I know it's not exactly what you want, but it seems to be working.

这是我找到的一件作品。我知道这并不是你想要的,但它似乎正在起作用。

Step 1: Declare the function you'd like with an array instead of variadic arguments:

步骤1:声明您希望使用数组而不是变量参数的函数:

func sumOf(numbers: [Int]) -> Int {
    var total = 0
    for i in numbers {
        total += i
    }
    return total
}

Step 2: Call this from within your variadic function:

步骤2:从变量函数内部调用:

func sumOf(numbers: Int...) -> Int {
    return sumOf(numbers)
}

Step 3: Call Either Way:

第三步:用任何一种方式打电话:

var variadicSum = sumOf(1, 2, 3, 4, 5)
var arraySum = sumOf([1, 2, 3, 4, 5])

It seems strange, but it is working in my tests. Let me know if this causes unforeseen problems for anyone. Swift seems to be able to separate the difference between the two calls with the same function name.

这看起来很奇怪,但在我的测试中它起作用了。如果这会给任何人带来不可预见的问题,请告诉我。Swift似乎能够区分具有相同功能名称的两个调用之间的差异。

Also, with this method if Apple updates the language as @manojid's answer suggests, you'll only need to update these functions. Otherwise, you'll have to go through and do a lot of renaming.

此外,如果苹果按照@manojid的回答更新了语言,那么只需更新这些函数。否则,您将不得不进行大量重命名。

#3


12  

You can cast the function:

您可以设置函数:

typealias Function = [Int] -> Int
let sumOfArray = unsafeBitCast(sumOf, Function.self)
sumOfArray([1, 2, 3])

#4


11  

You can use a helper function as such:

你可以使用辅助功能:

func sumOf (numbers : [Int])  -> Int { return numbers.reduce(0, combine: +) }
func sumOf (numbers : Int...) -> Int { return sumArray (numbers) }

#5


1  

I did this (Wrapper + Identity Mapping):

我做了这个(包装器+身份映射):

func addBarButtonItems(types: REWEBarButtonItemType...) {
    addBarButtonItems(types: types.map { $0 })
}

func addBarButtonItems(types: [REWEBarButtonItemType]) {
    // actual implementation
}

#6


0  

I know this response does not answer your exact question, but I feel its worth noting. I too was starting to play with Swift and immediately ran into a similar question. Manojlds answer is better for your question, I agree, but again, another workaround I came up with. I do happen to like Logan's better too.

我知道这个回答不能回答你的确切问题,但我觉得它没有什么价值。我也开始和斯威夫特比赛,很快就遇到了类似的问题。Manojlds的回答更适合你的问题,我同意,但是我又想出了另一个解决方案。我也很喜欢洛根。

In my case I just wanted to pass an array:

在我的例子中,我只想传递一个数组:

func sumOf(numbers: Array<Int>) -> Int {
    var sum = 0
    for number in numbers {
        sum += number
    }
    return sum
}

var someNums = [8,7,2,9,12]
sumOf(someNums)
sumOf([10, 15, 20])

Just wanted to share, in case anyone else was thinking like me. Most of the time I would prefer pass the array like this, but I don't think the "Swiftly" yet. :)

我只是想分享,以防别人也像我一样思考。大多数时候,我更喜欢像这样传递数组,但我不认为“迅速”。:)

#1


79  

Splatting is not in the language yet, as confirmed by the devs. Workaround for now is to use an overload or wait if you cannot add overloads.

正如开发人员所证实的,溅射还没有出现在语言中。目前的解决方案是使用重载,如果不能添加重载,则等待。

#2


55  

Here's a work around that I found. I know it's not exactly what you want, but it seems to be working.

这是我找到的一件作品。我知道这并不是你想要的,但它似乎正在起作用。

Step 1: Declare the function you'd like with an array instead of variadic arguments:

步骤1:声明您希望使用数组而不是变量参数的函数:

func sumOf(numbers: [Int]) -> Int {
    var total = 0
    for i in numbers {
        total += i
    }
    return total
}

Step 2: Call this from within your variadic function:

步骤2:从变量函数内部调用:

func sumOf(numbers: Int...) -> Int {
    return sumOf(numbers)
}

Step 3: Call Either Way:

第三步:用任何一种方式打电话:

var variadicSum = sumOf(1, 2, 3, 4, 5)
var arraySum = sumOf([1, 2, 3, 4, 5])

It seems strange, but it is working in my tests. Let me know if this causes unforeseen problems for anyone. Swift seems to be able to separate the difference between the two calls with the same function name.

这看起来很奇怪,但在我的测试中它起作用了。如果这会给任何人带来不可预见的问题,请告诉我。Swift似乎能够区分具有相同功能名称的两个调用之间的差异。

Also, with this method if Apple updates the language as @manojid's answer suggests, you'll only need to update these functions. Otherwise, you'll have to go through and do a lot of renaming.

此外,如果苹果按照@manojid的回答更新了语言,那么只需更新这些函数。否则,您将不得不进行大量重命名。

#3


12  

You can cast the function:

您可以设置函数:

typealias Function = [Int] -> Int
let sumOfArray = unsafeBitCast(sumOf, Function.self)
sumOfArray([1, 2, 3])

#4


11  

You can use a helper function as such:

你可以使用辅助功能:

func sumOf (numbers : [Int])  -> Int { return numbers.reduce(0, combine: +) }
func sumOf (numbers : Int...) -> Int { return sumArray (numbers) }

#5


1  

I did this (Wrapper + Identity Mapping):

我做了这个(包装器+身份映射):

func addBarButtonItems(types: REWEBarButtonItemType...) {
    addBarButtonItems(types: types.map { $0 })
}

func addBarButtonItems(types: [REWEBarButtonItemType]) {
    // actual implementation
}

#6


0  

I know this response does not answer your exact question, but I feel its worth noting. I too was starting to play with Swift and immediately ran into a similar question. Manojlds answer is better for your question, I agree, but again, another workaround I came up with. I do happen to like Logan's better too.

我知道这个回答不能回答你的确切问题,但我觉得它没有什么价值。我也开始和斯威夫特比赛,很快就遇到了类似的问题。Manojlds的回答更适合你的问题,我同意,但是我又想出了另一个解决方案。我也很喜欢洛根。

In my case I just wanted to pass an array:

在我的例子中,我只想传递一个数组:

func sumOf(numbers: Array<Int>) -> Int {
    var sum = 0
    for number in numbers {
        sum += number
    }
    return sum
}

var someNums = [8,7,2,9,12]
sumOf(someNums)
sumOf([10, 15, 20])

Just wanted to share, in case anyone else was thinking like me. Most of the time I would prefer pass the array like this, but I don't think the "Swiftly" yet. :)

我只是想分享,以防别人也像我一样思考。大多数时候,我更喜欢像这样传递数组,但我不认为“迅速”。:)