2011-01-19 15 views
5

次のようなインラインとして関数を宣言することができます:あなたはDEBUGにいないとき、それを最適化し、インラインているため、機能に費用はかかりません。Objective-Cで静的クラスメソッドをインライン化できますか?

#ifdef DEBUG 
void DPrintf(NSString *fmt,...); 
#else 
inline void DPrintf(NSString *fmt,...) {} 
#endif 

ように。あなたは同じことをしたいが、クラスメソッドの場合はどうですか?

私のクラスは、このように宣言されています

@interface MyClass : NSObject { 

} 

    + (void)DPrintf:(NSString *)format, ...; 
    // Other methods of this class 
@end 

私はメソッドを呼び出すに費用はかかりませんようにinlineに似たものに「DPrintf」を変換したいです。

しかし、私はこれを行うことはできません。

inline +(void)DPrintf:(NSString *)format, ...; {} 

は、どのように私は非デバッグコンパイルのためにオフになったクラスのゼロコストの静的メソッドを持つことができますか?

答えて

8

注意してください。 Objective-CメソッドはC関数と同じではありません。 Objective-Cメソッドはコンパイラによってobjc_msgSend()関数呼び出しに変換されます。メソッドがインラインであるかどうかは、それが無関係であるため制御できません。 Objective-Cランタイムhere (Objective-C Runtime Programming Guide)here (Objective-C Runtime Reference)、およびhere (CocoaSamurai post)について詳しく読むことができます。すばらしいGoogle検索で詳細を表示する必要があります。

+4

また、時期尚早の最適化に注意してください。印刷物である関数のインラインマーキングは、たとえその関数が多く呼び出されても、時間を節約することはできません。インライン化は、リターンが非常に計算が簡単な場合にのみ意味があります。そのため、関数呼び出しのオーバーヘッドは重要です。 printfのバリエーションを何も伴わないものは、呼び出される命令の数の面で簡単です。 –

+4

今日、最も現代的なコンパイラ(GCCかClangのいずれか)は、インラインでうまく機能する関数を認識する方法を一般に知っており、それ自体をそのようにマークします。コンパイラがインラインで関数をマークするかどうかを無視するCコンパイラもあると聞いたことがあるので、コンパイラがそれをそのままにしておくことをお勧めします。注意してください)。 –

6

Objective-Cに静的メソッドはありません。クラスメソッドは、クラスに属している以外はインスタンスメソッドと似ています。これは、インスタンスメソッドと同様に、クラスに送信されるメッセージは、呼び出しの正しいメソッドを決定するためにメッセージディスパッチ機構を経由しなければならず、実行時に行われることを意味します。メソッドディスパッチ機械への呼び出しをインライン展開することはできますが、Objective-Cコンパイラには現時点で存在しない狂ったレベルの最適化がなければ、メソッド本体をインライン化することはできません。

いずれにせよ、これはマイクロ最適化です。プロファイリングが必要であることが示されている場合(ほとんど決してありません)、体操を通過できます。それ以外の場合は、アプリケーションの実際のパフォーマンスに関する懸念を心配してください。

+3

クラスのメソッドと静的メソッドが同義であるJavaのバックグラウンドから来るものについては、Objective-Cクラスのメソッドは動的に解決されることに注意してください。クラスオブジェクトは静的ではないからです。 http://en.wikipedia.org/wiki/Method_(computer_programming) –

関連する問題