2012-02-16 9 views
5

名前空間やプロジェクトフォルダ構造がアセンブリのパフォーマンスに影響を与えるかどうかは疑問です。私の腸は"いいえ、コンパイル時に影響する可能性があります"と言っています。名前空間またはフォルダ構造がアセンブリのパフォーマンスに影響しますか?

パフォーマンスについて考えてみると、特にあなたが初心者の方であれば、いつもうまくいくと思います。私はそれを助けることができない!だから、尊敬して賞賛する仲間のゲーム開発者に尋ねると思った。

+0

私は@PlayDeezGamesの答えと競争したくありません:それは本当にしません。動的言語では、それは可能性があります。 SQL Serverでは、最大30%のコストを払うことができます。決してC#で。 –

答えて

17

未熟な最適化がどのように悪い考えであるかは誰もが説明しましたが、実際には何の違いもありません(後でリフレクションを使用する場合を除きます)。

コード

CLRの静的リファレンス(したがって、MSIL - C#はにコンパイルするものである)、実際に名前空間の概念や考え方を持っていません。タイプ(クラス、列挙型など)はフルネーム(例:System.Runtime.Serialization.ISerializable)で表され、「フルストップ」は名前の他の文字と同じように不透明(意味があります)です。名前空間の全体概念は、C#(またはあなたが使用している言語)が提供するものです。しかし、生のMSILに関しては、型名は実際には問題ではありません。

MSILでは、名前で何かを決して参照しません。アセンブリ(dllまたはexe)のすべてには、特定の種類のハンドルがあります。たとえば、タイプはTypeHandleで、タイプに含まれるものはMemberHandleです。両方とも32ビット整数です。だから、メソッドを呼び出すときには、call <MethodName> on <TypeName> in <Assembly>をMSILに書くのではなく、call <MethodHandle> on <TypeHandle> in <Assembly>と書いてください。したがって、名前に5000文字のタイプを取得するには、5つのタイプと同じ時間がかかります。実際の名前はアセンブリ内の別の場所に格納されます。リフレクションを使用してコンパイラを使用できるようにするだけです(つまり、名前は「あなたの情報のために」格納されます)。これはメタデータと呼ばれます。

私は生のMSILを与えるILDASMを得る方法があると思いますが、わかりません。文字列の比較はO(n)を操作している:あなたが欲しいタイプ名と、それが違いをアセンブリで利用可能な名前の間に文字列の比較を行っているので、反射

を使用してアクセス

。しかし、今度は小文字でとなり、は完全に無視して(差がナノ秒になります)です - それでも心配しないでください。

概要

これは時期尚早の最適化は本当に悪いです理由です - あなたは、これが現実でそれを行う方法はありません速くなったり遅くあり、ボトルネックだったと仮定。

+0

'/ bytes'を' ildasm'に渡すと、ILのopcodeや(該当する場合)トークンやハンドルを含む、たくさんの16進コードが表示されます。生の形式でメタデータテーブルをダンプすることもできます。 @ JoshPetrie確かに –

+0

。私はオプションを "ILの命令のためにもっと行きますが、名前を検索しないでください" - 私は**それが持っていたと思う:私はセシルとildasmを混ぜていない限り。 *編集:*ああ、それはおそらくそれだった。 –

+0

+1質問に答えて*理由を説明するため。 –

19

回答:いいえ、プロジェクトのフォルダ構造と名前空間は、パフォーマンスに大きな影響を与えません。

パフォーマンスについての言葉。

ことが書かれている:

早期の最適化は諸悪の根源です。

私は初心者です。

私は今までに最高のコードを手に入れたいと思っていました。

私は同じことが欲しいと思います。

しかし、このようなことを心配することはあなたを助けません。

ちょうどいくつかのゲームを書き、いくつかの経験を積む。

後でパフォーマンスが心配です。

+2

私は[俳句(http://en.wikipedia.org/wiki/Haiku)を期待しています! –

+0

+1の詩! – kaoD

+0

とても信じられないほど正確です+1 – Valmond

-1

確かに名前空間は単なるC++のものです。 EG、xbox359逆アセンブラでは、名前空間のようなものにブレークポイントはありません。 blahblah :: peoplewhosefooのようなものは、388 < 000000>に沸騰するでしょう。私が覚えているのであれば、現在のポイントのスタックポインタは+ < 000000>バイトにジャンプします。これは、上記の機能である可能性があります。他の人が(まだこの部分の専門家ではないかもしれませんが)スタックフレームのロードローカルを作成し、r4にr < ...>のパラメータを入れてください。

しかし、このテキストをすべて無視して、最初に30fpsのゲームを作成してから、コードのホットスポット/ボトルネックを見つけて修正することができます。この%0.01最適化ではなく。

これは、上記の他の回答で効果的に述べられていることです。

+0

彼はC++についてではなく、C#について話しています。しかし、ほとんどの場合、コンパイル時にしか処理されていない可能性があります。 (そしておそらく、コードがリフレクションを行っているのであれば、それは珍しいことです) – Kylotan

+0

ああ、私はタグを気付かなかった。 –

3

ソースファイルをディスクに編成しても、コンパイルされたアセンブリのパフォーマンスには影響しません。また、ネームスペースの深さや幅もソースコード内で使用されることはありません。

CLI(#335)のECMA規格、特にパーティションIIの第22章を参照すると、アセンブリのタイプを記述するために使用されるメタデータ形式(TypeDef論理表)が見つかります。そこには、タイプ名とタイプ名前空間が両方とも、文字列へのインデックスであることがわかります。CLIメタデータのヒープインデックスは、すべての使用可能なアイテムのインデックスに必要な最小サイズになるように設計されているため、擬似動的です。実際のバイト数における文字列ヒープインデックスのサイズは変わるかもしれませんが、すべてのタイプで同じになります。

したがって、メタデータを介した名前空間または名前へのアクセスは、そのアセンブリのスコープ内で一定の時間になります。名前空間インデックスを囲むデータへのアクセスは、同様に一定時間になります(実際の文字列はヒープにあるため、タイプメタデータの名前空間文字列を「過去にスキップする」ために線形時間文字列長の計算を行う必要はありません) 。

名前空間が実際にどれだけ深く入れ子になっているかは、リフレクションによってコードにアクセスし、それらに対して線形時間の文字列操作を開始するまでは実際には(*)問題ではありません。しかし、その時点であなたが実行する文字列操作には当てはまります。

(*)ユニークな名前空間と名前と他の文字列のは明らかに文字列ヒープのサイズが大きくなりますが、パフォーマンス上の、これは持っている任意の影響は極めて低レベルで、常に必ずしも否定的ではありません。

関連する問題