> On Nov 10, 2017, at 3:27 PM, Charles Srstka <[email protected]> wrote:
> 
>> On Nov 10, 2017, at 2:57 PM, Joe Groff <[email protected]> wrote:
>> 
>>> On Nov 10, 2017, at 12:37 PM, Charles Srstka <[email protected]> 
>>> wrote:
>>> 
>>>> On Nov 10, 2017, at 12:04 PM, Joe Groff via swift-evolution 
>>>> <[email protected]> wrote:
>>>> 
>>>> I don't like the idea of some calls having wildly different semantics from 
>>>> others; it's difficult enough to tell what exactly a call might be doing 
>>>> already. Since we also lack the more obvious static "Callable" protocol 
>>>> idea to give even well-typed call syntax to user-defined types, this also 
>>>> seems like it'd be easily abused for that purpose too.
>>> 
>>> We already have that though, with the Objective-C bridge. How is the 
>>> proposed behavior here more wildly different than the semantics of 
>>> non-@objc, @objc, and @objc dynamic calls?
>> 
>> The language semantics aren't any different for non-@objc or @objc calls. 
>> The dispatch mechanism is an implementation detail. `dynamic` admits the 
>> possibility of late binding to change the method implementation dynamically, 
>> but doesn't change the type system behavior of the method, or radically 
>> change the implementation mechanism; it's still ultimately an indirect call, 
>> it doesn't turn your argument list into a dictionary that can be arbitrarily 
>> interpreted by user code.
>> 
>> -Joe
> 
> You sure about that? ;-)
> 
> MyObject.h:
> 
> #import <Foundation/Foundation.h>
> 
> @interface MyObject : NSObject
> 
> @property (nonatomic, copy) void (^callback)(NSDictionary *);
> 
> @end
> 
> @interface MyObject (MyCategory)
> 
> - (void)foo:(NSString *)foo bar:(NSString *)bar;
> 
> @end
> 
> MyObject.m:
> 
> #import "MyObject.h"
> 
> @implementation MyObject
> 
> - (void)baz:(NSString *)baz qux:(NSString *)qux {}
> 
> - (NSMethodSignature *)methodSignatureForSelector:(SEL)selector {
>     if (selector == @selector(foo:bar:)) {
>         return [super methodSignatureForSelector:@selector(baz:qux:)];
>     } else {
>         return [super methodSignatureForSelector:selector];
>     }
> }
> 
> - (void)forwardInvocation:(NSInvocation *)invocation {
>     NSString *name = NSStringFromSelector(invocation.selector);
>     NSMutableArray *args = [NSMutableArray new];
>     
>     for (NSUInteger i = 2; i < invocation.methodSignature.numberOfArguments; 
> i++) {
>         __unsafe_unretained id obj = nil;
>         
>         [invocation getArgument:&obj atIndex:i];
>         
>         [args addObject:obj];
>     }
>     
>     self.callback(@{ @"name" : name, @"arguments" : args });
> }
> 
> @end
> 
> main.swift:
> 
> import Foundation
> 
> let obj = MyObject()
> 
> obj.callback = { dict in
>     print("got this dictionary: \(dict as? [String : Any] ?? [:])")
> }
> 
> obj.foo("Foo", bar: "Baz”)

How `MyObject.foo(_:bar:)` gets implemented is its own business, as far as the 
compiler is concerned. The compile-time name resolution for the method isn't 
impacted.

-Joe
_______________________________________________
swift-evolution mailing list
[email protected]
https://lists.swift.org/mailman/listinfo/swift-evolution

Reply via email to