Reputation: 7330
the constructor is receiving two parameters.
a) a function whose type is a function receiving an inout params (so it can change the params)
b) passing your params object, expecting the function passed will be able to modify the object
then trigger the apply method, so your passed function can change the passed params.
If there's a solution with passing params in a closure, that'd work too.
class Test {
var params: Any?
var myFunc: (inout params: Any?) -> () = { (inout params: Any?) in return } //default value
//constructor receving a function and a address to inout params object
init(myFunc: (inout params: Any?) -> (), inout params: Any?) {
self.myFunc = myFunc
self.params = params
}
//call the passed function (extern) and pass the address of given params
func apply() {
self.myFunc(params: &self.params)
}
}
func extern(inout params: Any?) {
var a = params as [String: Int]
a["factor"] = 11
}
var p: Any = ["factor": 10]
var test = Test(myFunc: extern, params: &p)
test.apply() //p["factor"] should be 11 now here
p["factor"] as [String: Int]
My second attempt using closures
//Utility
class Test {
var closure: () -> Any
var myFunc: (message: String, closure: () -> Any) -> () = { (message: String, closure: () -> Any) in return }
init(myFunc: (message: String, closure: () -> Any) -> (), closure: () -> Any) {
self.myFunc = myFunc
self.closure = closure
}
func apply(message: String) {
self.myFunc(message: message, closure: self.closure)
}
}
//users of the utility
func extern(message: String, closure: () -> Any) {
println(message)
var name = closure() as [String: String]
name["name"] = "Doe"
}
var name: Any = ["name": "John"]
var test = Test(myFunc: extern, closure: {name})
test.apply("hello ")
name //it's still John here
3rd attempt using AnyObject and closures and of course it works but still need your opinion guys for a best strategy.
//Utility
class Test {
var closure: () -> AnyObject
var myFunc: (message: String, closure: () -> AnyObject) -> () = { (message: String, closure: () -> AnyObject) in return }
init(myFunc: (message: String, closure: () -> AnyObject) -> (), closure: () -> AnyObject) {
self.myFunc = myFunc
self.closure = closure
}
func apply(message: String) {
self.myFunc(message: message, closure: self.closure)
}
}
//users of the utility
func extern(message: String, closure: () -> AnyObject) {
println(message)
var name: Name = closure() as Name
name.name = "Doe"
}
class Name {
var name = "John"
}
var name = Name()
var test = Test(myFunc: extern, closure: {name})
test.apply("hello ")
name //it's changed here
Upvotes: 0
Views: 563
Reputation: 93276
It seems like you're trying to reinvent closures here. One point of closures is that they can capture references to the values around them. This should do what you're describing above, and lets you keep using proper types for your variables, rather than falling back on Any
:
class Test {
var myFunc: () -> Void = { }
init(myFunc: () -> Void) {
self.myFunc = myFunc
}
func apply() {
self.myFunc()
}
}
func extern(inout dict: [String: Int]) {
dict["factor"] = 11
}
var p = ["factor": 10]
let test = Test {
extern(&p)
}
test.apply() // p["factor"] is now 11 here
println(p)
// ["factor": 11]
Upvotes: 1