Swift - 'Bool' Is Not a Subtype of 'Void'

Swift - 'Bool' is not a subtype of 'Void'?

The argument to performBlock is a closure taking no arguments and returning Void
(i.e. no return value).
If the closure consists of a single expression, the return type is inferred from
the type of that expression. The type of

self.managedObjectContext.save(nil)

is Bool, which cannot implicitly be converted to Void.
To fix that problem, you can add an explicit return statement:

self.managedObjectContext.performBlock {
self.managedObjectContext.save(nil)
return
}

or (better), check the return value of the save operation instead of ignoring it:

self.managedObjectContext.performBlock {
var error : NSError?
if !self.managedObjectContext.save(&error) {
// report error
}
}

(and do the same for the outer level save).


Update: As of Swift 1.2 (Xcode 6.3), unannotated single-expression closures with non-Void return types can now be used in Void contexts. So this does now compile without errors:

self.managedObjectContext.performBlock {
self.managedObjectContext.save(nil)
// explicit "return" not needed anymore in Swift 1.2
}

(Of course it is still better to actually check the return value
from the save operation.)

SKNode!' is not a subtype of 'SKNode'

In the SKNode class, the block argument to this message is of the type (void (^)(SKNode *node, BOOL *stop))

When Swift imports an Objective-C class, all of its message arguments and return values are imported as optionals -- arguments you pass to functions are always NSString? or NDSData?, not just NSString or NSData. They do this because all pointers in Obj-C can be nil, but a var in Swift can't be nil unless it has a question mark at the end, thus making it an "optional" type.

So when you define your enmuerationBlock, it should be of the type

(SKNode?, CMutablePointer<ObjCBool>) -> Void


EDIT answering flainez's question below:

When you have a mutable pointer, you dereference it by obtaining an UnsafePointer thus

var val :CMutablePointer<Bool> = /* get this from somewhere */

val.withUnsafePointer() { (p :UnsafePointer<Bool>) in
p.memory = true /* or whatever */
}

.withUnsafePointer yields an UnsafePointer<T> to the block, and UnsafePointer<T> has a memory property that is assignable.

Annoying: You can't test this in the Playground's REPL, it always fails, but it works when you compile it to a proper target.

Cannot call value of non-function type '((AnyClass) - Bool)!'

I have found the solution,its simple

 let myDeepLinkAction: UAAction = UAAction(block: {(args:UAActionArguments, handler:UAActionCompletionHandler) -> Void in
handler(UAActionResult.empty())
}, acceptingArguments: {(arguments: UAActionArguments) in

if arguments.situation == UASituation.backgroundPush {

return true
}
return (arguments.value! is NSString || arguments.value! is URL)

})

return (arguments.value! is NSString || arguments.value! is URL)

Closures causing error Swift

If you need to pass a bool into the closure, you have to change the typealias from () -> Void to Bool -> Void. In addition, your registrationSucceededForUser function will need to be changed so the callback is passed in as a parameter. Right now, you're "invoking" a function signature, not an actual function.

Also, some line breaks in the registerUser function signature will go a long way for readability.

typealias LoginCompletionBlock = Bool -> Void
model.registerUser(usernameTextField.text, emailID: emailTextField.text,
password: passwordTextField.text, profileImage: profileImageView.image!,
registrationMethod: "normal", onCompletion: {
success in
//Perform actions after login
})
}

edit: I've added the specific modifications I might make to the code. More information may be needed to actually understand the root of the type error. Note that if the body of your inline closure consists of one statement, it can be inferred to be the return value, and you may need to add newline and an empty return statement to satisfy the Void return type.

Cannot convert value of type '() - ()' to expected argument type '(LongPressGesture.Value) - Void' (aka '(Bool) - ()')

You would need to change your startTimer signature to accept LongPressGesture.Value (which resolves to Bool):

func startTimer(_ value : LongPressGesture.Value) {
//
}
LongPressGesture(minimumDuration: 0.25).onEnded(startTimer)

Cannot convert the expression's type' with optional in closure body

An expression containing a single expression is inferred to return that result, hence:

let closure: (number: Int) -> Void = { (number) -> Void in
optional?.updateValue(number, forKey: "key")
}

is equivalent to:

let closure: (number: Int) -> Void = { (number) -> Void in
return optional?.updateValue(number, forKey: "key")
}

You now have conflicting return types between Void and Int? (remember, updateValue returns the old value)

Splitting it up with an explicit return clarifies the inferred typing.

let closure: (number: Int) -> Void = { (number) -> Void in
optional?.updateValue(number, forKey: "key")
return
}


Related Topics



Leave a reply



Submit