内部で単一のメソッド呼び出しによって変化するメソッドがあり、それが変化するメソッドのメソッド/シグネチャを引数として渡したい...これはObjective Cで可能ですか、それとも期待するには多すぎますか?為に?
3 に答える
NSInvocation は、メソッド呼び出しをオブジェクトにラップするためのクラスです。セレクター (メソッド シグネチャ) を設定し、引数をインデックスで設定できます。次に、ターゲットを設定して呼び出しを呼び出して呼び出しをトリガーするか、ターゲットを未設定のままにして、invokeWithTarget: を何らかのループで使用して、多くのオブジェクトでこれを呼び出すことができます。
次のように少し動作すると思います。
NSInvocation *inv = [[NSInvocation alloc] init];
[inv setSelector:@selector(foo:bar:)];
[inv setArgument:123 atIndex:0];
[inv setArgument:456 atIndex:1];
for (MyClass *myObj in myObjects) {
[inv invokeWithTarget:myObj];
}
または、呼び出しオブジェクトをこのメソッドに渡したくない場合は、SEL タイプを使用してセレクター (メソッド シグネチャ) を受け入れることができます。
-(void)fooWithMethod:(SEL)selector;
次に、セレクターを呼び出しオブジェクトに割り当てて、オブジェクトで呼び出します。
または、このfooWithMethod:(SEL)selector
アプローチを使用し[myObject performSelector:selector]
ている場合は、他に引数がない場合はそのまま実行してください。
詳細については、NSObject を参照してください。
前に述べたように、呼び出したいメソッドのセレクターを渡すことができます。セレクターを使用すると、実際にメソッドを呼び出すさまざまな方法があります。
NSObject
sperformSelector:
、performSelector:withObject:
およびperformSelector:withObject:withObject:
メソッドの使用NSInvocation
オブジェクトを使用する- または直接またはを使用し
objc_msgSend
てobjc_msgSend_stret
- 使用して
IMP
取得できるそのメソッドの を使用してmethodForSelector:
どちらを使用するかは、状況によって異なります。パフォーマンスが重要でない場合、0、1、または 2 つのオブジェクトを渡す必要がある場合は 1 を使用します。メソッドが一致しない場合はperformSelector:...
、2 または 3 を使用します。オブジェクトのセットアップにNSInvocation
は多くのボイラープレート コードが必要なので、3 を好みますが、パフォーマンスの問題がない限り、それは個人的な選択の問題だと思います。
これらのメソッド呼び出しのパフォーマンスが問題になる場合は、3 または 4 を使用します。s をキャッシュできない限り、3 の方が高速ですIMP
。ただし、コードによっては、これが実行できないか、実際には役に立たない場合があります。したがって、ここでコードをプロファイリングして、どちらが適しているかを確認する必要があります。