You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
I'm making use of `@convention(block)` tag to cast my blocks as objects and compare them later. I've read that Swift nor Objective C don't provide direct comparison due to complexity and other reasons, despite this method working pretty well in my situation. For me this is kind of an important feature, but I'm missing the ability to use `@convention(block)` directly on class methods.
By directly I mean that I can simply same class method to another variable casted with `lazy var swfBlock: ObjBlock = self.swf` and it would work as expected.
importFoundation// Some interesting observations on block comparing. Apparently swift nor objective c don't allow comparing closures// due to the complexity of the process and because of compiler optimisations… bla bla. But it seems to be possible// to do this using conventions blocks, aka the objective c ones that can be cast as objects. The interesting part // is how swift freely casts SwfBlock to ObjBlock, yet in reality two casted SwfBlock blocks will always be different// values, while ObjBlocks won't. When we cast ObjBlock to SwfBlock, the same thing happens to them, they become two// different values. So, in order to preserve the reference, this sort of casting should be avoided.typealiasSwfBlock = () -> ()
typealiasObjBlock = @convention(block) () -> ()
functestSwfBlock(a: SwfBlock, _b: SwfBlock) -> String {
letobjA = unsafeBitCast(aasObjBlock, AnyObject.self)
letobjB = unsafeBitCast(basObjBlock, AnyObject.self)
return"a is ObjBlock: \(a is ObjBlock), b is ObjBlock: \(b is ObjBlock), objA === objB: \(objA === objB)"
}
functestObjBlock(a: ObjBlock, _b: ObjBlock) -> String {
letobjA = unsafeBitCast(a, AnyObject.self)
letobjB = unsafeBitCast(b, AnyObject.self)
return"a is ObjBlock: \(a is ObjBlock), b is ObjBlock: \(b is ObjBlock), objA === objB: \(objA === objB)"
}
functestAnyBlock(a: Any?, _b: Any?) -> String {
if !(aisObjBlock) || !(bisObjBlock) {
return"a nor b are ObjBlock, they are not equal"
}
letobjA = unsafeBitCast(aas! ObjBlock, AnyObject.self)
letobjB = unsafeBitCast(bas! ObjBlock, AnyObject.self)
return"a is ObjBlock: \(a is ObjBlock), b is ObjBlock: \(b is ObjBlock), objA === objB: \(objA === objB)"
}
classFoo
{
lazyvarswfBlock: ObjBlock = self.swffuncswf() { print("swf") }
@objcfuncobj() { print("obj") }
}
letswfBlock: SwfBlock = { print("swf") }
letobjBlock: ObjBlock = { print("obj") }
letfoo: Foo = Foo()
print(testSwfBlock(swfBlock, swfBlock)) // a is ObjBlock: false, b is ObjBlock: false, objA === objB: falseprint(testSwfBlock(objBlock, objBlock)) // a is ObjBlock: false, b is ObjBlock: false, objA === objB: falseprint(testObjBlock(swfBlock, swfBlock)) // a is ObjBlock: true, b is ObjBlock: true, objA === objB: falseprint(testObjBlock(objBlock, objBlock)) // a is ObjBlock: true, b is ObjBlock: true, objA === objB: trueprint(testAnyBlock(swfBlock, swfBlock)) // a nor b are ObjBlock, they are not equalprint(testAnyBlock(objBlock, objBlock)) //a is ObjBlock: true, b is ObjBlock: true, objA === objB: trueprint(testObjBlock(foo.swf, foo.swf)) // a is ObjBlock: true, b is ObjBlock: true, objA === objB: falseprint(testSwfBlock(foo.obj, foo.obj)) // a is ObjBlock: false, b is ObjBlock: false, objA === objB: falseprint(testAnyBlock(foo.swf, foo.swf)) // a nor b are ObjBlock, they are not equalprint(testAnyBlock(foo.swfBlock, foo.swfBlock)) // a is ObjBlock: true, b is ObjBlock: true, objA === objB: true
The text was updated successfully, but these errors were encountered:
Block comparison, even in Objective-C, only compares pointers. Curried methods like self.doTheThing have to make a new closure value every time, since they don't have any way of knowing if one's been created before. The best you could do is find out if one closure has the same identity as another closure, but that doesn't actually tell you anything.
Additional Detail from JIRA
md5: 8fc61590c47864f685a070f61dff4949
Issue Description:
I'm making use of `@convention(block)` tag to cast my blocks as objects and compare them later. I've read that Swift nor Objective C don't provide direct comparison due to complexity and other reasons, despite this method working pretty well in my situation. For me this is kind of an important feature, but I'm missing the ability to use `@convention(block)` directly on class methods.
By directly I mean that I can simply same class method to another variable casted with `lazy var swfBlock: ObjBlock = self.swf` and it would work as expected.
The text was updated successfully, but these errors were encountered: