facing issue while calling nested function in swift ios - swift

func check(a: () -> ()){
func a(){
print("A Calling")
}
a()
}
Calling function
check {
print("Check Calling")
}
In the above code, i am not able to call a() function and it will directly be executing "check calling "
Result : "Check Calling"
When i am calling check function it should be execute a() function also and order should be
Result should be:
"A Calling"
"Check Calling"

The problem with the code in your question is that you do not call the nested function at all. It doesn't help that you've named it the same as the passed in function which is perhaps why you are having trouble isolating the issue.
This works
func check(completion: () -> Void) {
func localFunction() {
print("A Calling")
}
localFunction()
completion()
}
check {
print("Check Calling")
}
// Outputs:
//
// A Calling
// Check Calling

Related

Swift closures - force a closure to always complete

Is it possible to force a closure to be completed? In the same way that a function with a return value MUST always return, it would be ace if there was a way to force a closure to contain the syntax necessary to always complete.
For example, this code will not compile because the function does not always return a value:
func isTheEarthFlat(withUserIQ userIQ: Int) -> Bool {
if userIQ > 10 {
return false
}
}
In the exact same way, I would like to define a function with a closure, which will also not compile if the closure never returns. For example, the code below might never return a completionHandler:
func isTheEarthFlat(withUserIQ userIQ: Int, completionHandler: (Bool) -> Void) {
if userIQ > 10 {
completionHandler(false)
}
}
The code above compiles, but I was wondering if there is a keyword which enforces that the closure sends a completion handler in all cases. Maybe it has something to do with the Void in the above function?
No, there is no language construct that will result in a compiler error if you forget (or don't need) to call the completion handler under all possible conditions like a return statement.
It's an interesting idea that might make a useful enhancement to the language. Maybe as a required keyword somewhere in the parameter declaration.
There is no special keyword for what you want. But there is an interesting approach you can take into consideration, that won't compile:
func isTheEarthFlat(withUserIQ userIQ: Int, completionHandler: (Bool) -> Void) {
let result: Bool
defer {
completionHandler(result)
}
if userIQ > 10 {
result = false
}
}
that will do and is completionHandler is forced to be called:
func isTheEarthFlat(withUserIQ userIQ: Int, completionHandler: (Bool) -> Void) {
let result: Bool
defer {
completionHandler(result)
}
if userIQ > 10 {
result = false
} else {
result = true
}
}
Not sure it's a good pattern to use.
Here is an interesting technique I thought of. You define GuarenteedExecution and GuarenteedExecutionResult types.
A GuarenteedExecution is a wrapper around a closure, which is to be used in a context where the execution of the closure must be guaranteed.
The GuarenteedExecutionResult is the result of executing a GuarenteedExecution. The trick is to have a desired function, e.g. isTheEarthFlat, return a GuarenteedExecutionResult. The only way to obtain a GuarenteedExecutionResult instance is by calling execute(argument:) on a GuarenteedExecution. Effectively, the type checker features responsible for guaranteeing a return, are now being used to guarantee the execution of GuarenteedExecution.
struct GuarenteedExecutionResult<R> {
let result: R
fileprivate init(result: R) { self.result = result }
}
struct GuarenteedExecution<A, R> {
typealias Closure = (A) -> R
let closure: Closure
init(ofClosure closure: #escaping Closure) {
self.closure = closure
}
func execute(argument: A) -> GuarenteedExecutionResult<R> {
let result = closure(argument)
return GuarenteedExecutionResult(result: result)
}
}
Example usage, in a seperate file (so as to not have access to GuarenteedExecutionResult.init):
let guarenteedExecutionClosure = GuarenteedExecution(ofClosure: {
print("This must be called!")
})
func doSomething(guarenteedCallback: GuarenteedExecution<(), ()>)
-> GuarenteedExecutionResult<()> {
print("Did something")
return guarenteedCallback.execute(argument: ())
}
_ = doSomething(guarenteedCallback: guarenteedExecutionClosure)

Swift nested functions vs Closure Variables

I want to make a function that fetches a record from CloudKit, if it encounters a temporary network error the function should retry.
func fetchRecord(withRecordID recordID: CKRecordID, returnBlock: (optError: ErrorType?) -> Void){
func internalReturnBlock(optError optError: ErrorType?){
if NSThread.isMainThread() {
returnBlock(optError: optError)
}
else{
dispatch_async(dispatch_get_main_queue(), {
returnBlock(optError: optError)
})
}
}
func internalWork(){
privateDB.fetchRecordWithID(recordID) { (optRecord, optError) in
if let error = optError{
// IF NETWORK ERROR RETRY
internalWork()
}
else{
internalReturnBlock(optError: nil)
}
}
}
internalWork()
}
Here I define such function (simplified), If the fetch encounters an error it retries by calling the nested function internalWork()
My question is what would be the difference between using nested functions or creating local closure variables?
For example, here I change the internalReturnBlock to a closure variable:
func fetchRecord2(withRecordID recordID: CKRecordID, returnBlock: (optError: ErrorType?) -> Void){
var internalReturnBlock = { (optError: NSError?) in
if NSThread.isMainThread() {
returnBlock(optError: optError)
}
else{
dispatch_async(dispatch_get_main_queue(), {
returnBlock(optError: optError)
})
}
}
func internalWork(){
privateDB.fetchRecordWithID(recordID) { (optRecord, optError) in
if let error = optError{
// IF NETWORK ERROR RETRY
internalWork()
}
else{
internalReturnBlock(nil)
}
}
}
internalWork()
}
What are the differences between using a nested function vs a variable block?
Any advantages or problems?
There is no difference in effect. One is a declared function with a name, the other is anonymous. But they are both functions. And a function is a closure in Swift, so they are both closures.
An anonymous function is permitted to use some abbreviations of form, such as the omission of return in a one-liner that returns a value. But none of those abbreviations makes any ultimate effective difference.
However, an anonymous function in Swift has one feature a declared function does not — a capture list. This can help avoid retain cycles.
f {
[unowned self] in
return self.name
}
Also, an anonymous function is defined after the declaration of the function that takes it as a parameter, so it can use terms that appear in that declaration:
f(param:String) {
return param
}
But if you are not using those features, then it doesn't matter which you use. They work identically.

Can swift exit out of the root closure?

In Swift, if I'm inside of a closure, that is itself inside of another function, is there a way to exit out of the function itself?
Here's an example of what this might look like using closures from the GCDKit library.
func test() {
GCDQueue.Default.async {
print("Print me!")
return //Is there a statement that does this?
}.notify(.Main) {
print("Never print me.")
}
}
No there is not. Closures run in self-contained environments. For all you know, by the time that closure is executed, the thread on which test() was called is no longer executing the test() method.
Let's consider a simpler version that doesn't include any third-party libraries, extra queues, or other complexity. We'll just create a closure and immediately execute it.
func dothing(andPrint shouldPrint: Bool) {
let closure = {
guard shouldPrint else { return }
print("I printed!")
}
closure()
print("did it return?")
}
dothing(andPrint: false) // Prints "did it return?"
The return here exits the closure, not dothing. Since closure could be passed to some other function, or stored in a property and executed at some later time (possibly on a different queue as in your example), there's no way for the return to exit anything beyond itself. Consider if we were to refactor the creation of the closure into its own function:
func fetchClosure(andPrint shouldPrint: Bool) -> () -> Void {
return {
guard shouldPrint else { return }
print("I printed!")
}
}
func dothing(andPrint shouldPrint: Bool) {
let closure = fetchClosure(andPrint: shouldPrint)
closure()
print("did it return?")
}
dothing(andPrint: false) // Prints "did it return?"
It shouldn't be surprising this has the same behavior (otherwise this wouldn't be a simple refactor). Now imagine how it would (or even could) work if return behaved any other way.
Your example is just a much more complicated version of the same thing. return exits the closure.

How to create function with two closures as params in Swift?

I need to translate such a func from Objective-C to Swift language. But can't find an example and can't get how to send 2 closures into func in Swift.
For example, original function in Objective-C:
- (void)getForDemoDataWithToken:(Token *)token
onSuccess:(void(^)(NSArray *demoData))success
onFailure:(void(^)(NSError *error))failure {
}
I know to send 1 closure as param:
getForDemoDataWithToken(token) {(success: String) -> Void in
// some code here
print(success)
}
But, how to send two closures?
Thank you
What about this?
Declaration
func getForDemoDataWithToken(
token: Token,
onSuccess: (demoData:NSArray?) -> (),
onFailure: (error:NSError?) -> ()) {
}
Invocation
getForDemoDataWithToken(Token(),
onSuccess: { (demoData) -> () in
},
onFailure: { (demoData) -> () in
}
)
A more Swifty approach
I usually see Swift code where only one closure is used. So instead of 2 distinct onSuccess and onFailure closures you could have just completion.
Next we should remember that NSArray is compatible with Swift but it's not the Swiftest way to use an array.
Let's see an example where the 2 concepts above are applied.
func getForDemoData(token:Token, completion:(data:[Foo]?, error:NSError?) -> ()) {
}
You can invoke it with the trailing closure syntax.
getForDemoData(Token()) { (data, error) -> () in
if let data = data where error == nil {
// success!
} else {
// oh no... something wrong here
}
}
You should pass the closures as normal parameters, like this:
func acceptsTwoClosures(
onSuccess onSuccess: (success: String) -> Void,
onFailure: (failure: String) -> Void) {
onSuccess(success: "Ook")
onFailure(failure: "Eek")
}
acceptsTwoClosures(
onSuccess: { print("Success: \($0)") },
onFailure: { print("Failure: \($0)") }
)
// In the playground the above prints:
//
// Success: Ook
// Failure: Eek
The way that you used in the question is called trailing closure, and it only works for the closures that are the last arguments in the function signature.
From the documentation:
If you need to pass a closure expression to a function as the function’s final argument and the closure expression is long, it can be useful to write it as a trailing closure instead. A trailing closure is a closure expression that is written outside of (and after) the parentheses of the function call it supports.
For example, you could also re-write my suggested snippet from above like this:
acceptsTwoClosures(onSuccess: { print("Success: \($0)") }) {
print("Failure: \($0)")
}
.. as you can see, I can pass the second (i.e. the last) closure outside of acceptsTwoClosures call as a trailing closure, but I still have to pass the first one as a normal parameter.

Is there a shorthand for a function that takes no parameters and returns nothing? AKA () -> ()

The title says it all, I believe. I'm simply curious if the () -> () acting as a function's parameter...
class Test {
var isAwesome = true
func loadData (callback: () -> ()) {
callback();
}
}
... has a shorter version. That's it!
I'm not sure if there is a "Swift-way" to do it, but if you really want to shorten it:
typealias A = ()->() // alias this closure risking readability
class Test {
func loadData (callback:A) {
callback();
}
}
It is a bit of a hack I suppose.
As found in: Apple Inc. 'The Swift Programming Language'. iBooks. https://itun.es/nl/jEUH0.l
You can use the following syntax:
func someFunctionThatTakesAClosure(closure: () -> ()) {
// function body goes here
}
// here's how you call this function without using a trailing closure:
someFunctionThatTakesAClosure({
// closure's body goes here
})
// here's how you call this function with a trailing closure instead:
someFunctionThatTakesAClosure() {
// trailing closure's body goes here
}
I cannot find any documentation that specifies a different solution. Every instance I can find in the current docs/book shows it how you have it. Here is a good section that talks about it. You can however call your method with some pretty short notation:
loadData {
// ...
}
Rather than having to treat it as a normal parameter:
loadData({
// ...
})
You can also call it like:
loadData() {
// ...
}
I think there is no shorter-way: I can just imagine a type-alias (like #Benzi mentioned), but the effect seems not worth the hack.
func takeEmptyFunc(emptyFunc: ()->()) { emptyFunc() }
func emptyFunc() { println("Worked"); }
takeEmptyFunc() { emptyFunc() } // prints "Worked"