Swiftで動的にクラス作ってメソッド呼ぶ。しかも全く型情報がない状態で。要はjavascriptみたいなことがしたい
まとめ
- NSSClassFromString使う
- 引数が3つ以上だとperformSelectorは使えない
- SwiftだとNSInvocationは使えないので代わりにIMPを使う
- Class methodとInstance methodで呼び方ちょっと違う
- performSelectorの返り値の型は
Unmanaged<AnyObject>
でtakeUnretainedValue
を使う
引数が多いときのやり方で参考にしたobjcのコード
+ (id)initGraphRequestWithGraphPath:(NSString *)graphPath{ Class FBSDKGraphRequestClass = NSClassFromString (@"FBSDKGraphRequest"); id graph = [FBSDKGraphRequestClass alloc]; SEL aSelector = NSSelectorFromString(@"initWithGraphPath:parameters:"); IMP imp = [graph methodForSelector:aSelector]; id (*func)(id, SEL, id, id) = (void *)imp; graph = func(graph, aSelector, graphPath, @{}); return graph; }
Unmanaged<AnyObject>
の取り出し方
var unmanagedObject: Unmanaged
= someFunctionThatReturnsAnUnmanagedObject() var newValue: Type = unmanagedObject.takeRetainedValue as Type
takeRetainedValue
ってやつを使うみたい。でも、アプリがEXC_BAD_ACCESSかなんかだったかで落ちた。
takeUnretainedValue
だったら大丈夫だった。
ふーむ。allocしたのに、release漏れてるからとかなんだろうか。Swiftでは普通allocなんて書かないからあんまり普段考えないことだけど。
SwiftでIMPを呼ぶ
unsafeBitCastを使う。