Array of Functions in Swift

Array of functions in Swift

You can use an enum to put various functions into the Array and then extract the functions with a switch.

    enum MyFuncs {
case Arity0 ( Void -> Void )
case Arity2 ( (Int, String) -> Void)
}

func someFunc(n:Int, S:String) { }
func boringFunc() {}
var funcs = Array<MyFuncs>()
funcs.append(MyFuncs.Arity0(boringFunc))
funcs.append( MyFuncs.Arity2(someFunc))

for f in funcs {
switch f {
case let .Arity0(f):
f() // call the function with no arguments
case let .Arity2(f):
f(2,"fred") // call the function with two args
}
}

How can I create an array of functions?

It's definitely possible, just initialize the array as:

var pending = Array<(Void -> Void)>()

or even a fancier

var pending = Array<()->()>()

or

var pending: [(Void->Void)] = []

or

var pending: [(()->())] = []

or

var penguins: [<(") <(")] = [] // kidding

How to use an array of functions in Swift

I assume you need something like

    _ = funcs.first {
if case let MyFuncs.Arity2(f) = $0 {
f(2, "Fred")
return true
}
return false
}

Passing an array to a function with variable number of args in Swift

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.

Array of functions in swift (Output needs to be explained)

You are appending functions body to closureArray with no return type as the function type has no input parameters and no return type.

So only closureArray will contains 5 blocks of functions.

Each element is itself a function with only one print operation which will print the array index. But if these are called after the for loop these always print the latest value of i

So closureArray[0]() will call the 0th indexed function that will print only "5" as the latest value of i is 5 and will return void.

Explanation is very simple.

How to pass functions from class instance into array in Swift

Swift Arrays are homogeneous, but you can use Any to box any type at the expense of losing the type information, so yes you can stick all of your functions into a single array even though they have different types. I don't particularly think its a good idea, but it does in fact work:

import UIKit
import PlaygroundSupport


class Foo {
var array: [Any] = []

init() {
array = [ f1, f2 ]
}

func f1() -> Int {
return array.count
}

func f2(a: Int, b: Int) {
// ... the functions are all different.
}
}

maybe this is slightly less horrible if you use the Objective C run time, since its dynamic and you can use actually use perform selector with arguments to invoke the selectors, but I still don't recommend it:

import UIKit
import PlaygroundSupport


class Foo {
var array: [Selector] = []

init() {
array = [#selector(f1), #selector(f2) ]
}

@objc func f1() -> Int {
return array.count
}

@objc func f2(a: Int, b: Int) {
// ... the functions are all different.
}
}

EDIT:

Option 3, enum with associated values (come up with more meaningful names than I have here):

import UIKit
import PlaygroundSupport


class Foo {

enum Function {
case void_Int(() -> Int)
case intInt_Void((Int,Int) -> Void)
}

var array: [Function] = []

init() {
array = [.void_Int(f1), .intInt_Void(f2) ]
}

@objc func f1() -> Int {
return array.count
}

@objc func f2(a: Int, b: Int) {
// ... the functions are all different.
}
}

Addings functions to an array in swift

If you want to create an array of functions, and each function does not take parameters and returns noting you can do:

var cycle = [()->()]()
cycle.append(nameOfYourFunctionNoBrackets)

How to get an array from a C function in Swift?

In C,

H3Index* neighboring = calloc(maxNeighboring, sizeof(H3Index));
kRing(indexed, k, neighboring);

allocates memory for maxNeighboring elements of type H3Index and initializes the memory to zero. The address of that memory block (which is the address of the first element) is then passed to the kRing function.

It is possible to call calloc and free from Swift, but the easier to use API is Unsafe(Mutable)(Buffer)Pointer with its allocate() and deallocate() methods:

let neighboring = UnsafeMutableBufferPointer<H3Index>.allocate(capacity: maxNeighboring)
neighboring.initialize(repeating: 0)
kRing(indexed, k, neighboring.baseAddress)

Now you can print the values with

for i in 0..<maxNeighboring { print(neighboring[i]) }

or justs (because Unsafe(Mutable)BufferPointer is a collection that can be iterated over):

for neighbor in neighboring { print(neighbor) }

Eventually you must release the memory to avoid a memory leak:

neighboring.deallocate()

A simpler solution is to define a Swift array, and pass the address of the element storage to the C function:

var neighboring = Array<H3Index>(repeating: 0, count: maxNeighboring)
kRing(indexed, k, &neighboring)

for neighbor in neighboring { print(neighbor) }

neighboring is a local variable now, so that the memory is automatically released when the variable goes out of scope.

swift function returning an Array

In Swift Array is generic type, so you have to specify what type array contains. For example:

func myArrayFunc(inputArray:Array<Int>) -> Array<Int> {}

If you want your function to be generic then use:

func myArrayFunc<T>(inputArray:Array<T>) -> Array<T> {}

If you don't want to specify type or have generic function use Any type:

func myArrayFunc(inputArray:Array<Any>) -> Array<Any> {}

Return/Pass new array to function (Swift 5)

This should work

myFunction(["a","b","c"])

This works equally well if you want to return an array from a func

func test() -> [String] {
return ["a", "b"]
}

And it works equally well with a custom class

MyOtherClass(name:"Test", someotherinfo:"Bla", 
myclassarray: [MyClass(name: "A", number: 1, content: "AAA"),
MyClass(name: "B", number: 2, content: "BBB")])


Related Topics



Leave a reply



Submit