86
public:
     inline int GetValue() const {
          return m_nValue;
     }
     inline void SetValue(int nNewValue) {
          this -> m_nValue = nNewValue;
     }

Learn C ++で、彼らはそれがより速く実行されるだろうと言った。だから、ゲッターやセッターに使ってみたらいいなと思いました。しかし、多分、それにはいくつかの欠点がありますか?

4

11 に答える 11

75

プロファイラーから、インライン化しないとパフォーマンスの問題が発生することが具体的に示されるまで、何もインライン化しません。

C ++コンパイラは非常にスマートで、ほぼ確実にこのような単純な関数を自動的にインライン化します。そして、通常、それはあなたよりも賢く、インライン化すべきかどうかを決定する上ではるかに優れた仕事をします。

インライン化するかどうかを考えずに、ソリューションに集中します。後でキーワードを追加することinline(これはインラインBTWを保証するものではありません)は非常に簡単で、プロファイラーを使用して潜在的な場所を簡単に見つけることができます。

于 2010-06-10T18:25:08.310 に答える
32

それらを定義内に記述するとinline 、デフォルトで考慮されます

これは、それらが実際インライン化されるのではなく、複数のコンパイル単位で許可されることを意味します(クラス定義自体は通常、複数のコンパイル単位で表示されるため) 。

于 2010-06-10T18:26:13.367 に答える
16

これは、パブリックAPIの悪い習慣です。これらの関数を変更するには、すべてのクライアントを再コンパイルする必要があります。

一般に、ゲッターとセッターがあると抽象化が不十分になります。そうしないでください。別のクラスの生データに絶えずアクセスする場合は、クラスを再配置する必要があります。代わりに、クラス内のデータをどのように操作するかを検討し、そのための適切なメソッドを提供します。

于 2010-06-10T18:27:44.063 に答える
11

ネガティブな点:

  1. コンパイラはあなたを無視することができます。

  2. これらの機能を変更するには、すべてのクライアントを再コンパイルする必要があります。

  3. 優れたコンパイラは、適切な場合、インライン化されていない関数をインライン化します。

于 2010-06-10T18:25:44.820 に答える
5

また、フレームごとに数百万のget / setを実行していない限り、これらがインラインであるかどうかはほとんど関係ありません。正直なところ、眠りを失う価値はありません。

また、declaration +definitionの前に「inline」という単語を置いたからといって、コンパイラがコードをインライン化するわけではないことに注意してください。さまざまなヒューリスティックを使用して、それが理にかなっているかどうかを判断します。これは、多くの場合、速度とサイズの古典的なトレードオフです。ただし、VC ++には少なくとも力ずくの「__forceinline」キーワードがあり(GCCに何があるかはわかりません)、コンパイラーの派手なヒューリスティックを踏みにじります。私は本当にそれをまったくお勧めしません、そしてあなたが別のアーキテクチャに移植すると、それはおそらく間違っているでしょう。

すべての関数定義を実装ファイルに入れて、ヘッダーの純粋な宣言を残してください(もちろん、テンプレートメタプログラミング(STL / BOOST / etc)の場合を除きます。この場合、ほとんどすべてがヘッダーにあります;))

人々がインライン化するのが好きな古典的な場所の1つ(少なくとも私の出身地であるビデオゲームでは)は、数学のヘッダーにあります。クロス/ドット積、ベクトルの長さ、行列のクリアなどは、ヘッダーに配置されることがよくありますが、これは不要だと思います。9/10パフォーマンスに違いはありません。大きなベクトル配列を行列で変換するなど、タイトなループを実行する必要がある場合は、手動で数学をインラインで実行するか、コーディングする方がよいでしょう。プラットフォーム固有のアセンブラ。

ああ、そして別のポイントとして、クラスがコードよりも多くのデータである必要があると感じた場合は、抽象化のOOの手荷物をもたらさない、古き良き構造体の使用を検討してください。:)

申し訳ありませんが、それほど多くのことを続けるつもりはありませんでしたが、実際のユースケースを検討するのに役立つと思います。

幸運を。

シェーン

于 2010-06-10T23:43:51.947 に答える
3

ヘッダーにコードを配置することで、内部クラスの動作を公開します。クライアントはこれを見て、クラスがどのように機能するかを推測することができます。これにより、クライアントコードを壊さずに、後でクラスを変更することがより困難になる可能性があります。

于 2010-06-10T18:30:11.720 に答える
2

コードは少し長くコンパイルされ、カプセル化が失われます。すべてはプロジェクトのサイズとその性質に依存します。ほとんどの場合、複雑なロジックがない場合は、インライン化しても問題ありません。

ところで、inlineクラス定義に直接実装する場合はスキップできます。

于 2010-06-10T18:24:32.570 に答える
2

あなたの場合、インラインキーワードは無意味です

コンパイラは、キーワードに関係なく、可能であり、必要に応じて関数をインライン化します。

キーワードinlineは、インライン化ではなくリンクに影響します。少し紛らわしいですが、よく読んでください。

定義が呼び出しとは異なるコンパイル単位(基本的にはプリプロセッサの後のソースファイル)にある場合、インライン化は、プロジェクト全体の最適化とリンク時コード生成が有効になっている場合にのみ可能になります。これを有効にすると、リンク時間が大幅に長くなります(リンカー内のすべてが実際に再コンパイルされるため)が、明らかにパフォーマンスが向上する可能性があります。GCCとVSでデフォルトでオンかオフかわからない。

于 2015-12-01T14:11:50.887 に答える
1

気にする必要はないと思います。インライン化に関するFAQセクションをお読みください。

于 2010-06-10T18:28:14.503 に答える
1

少なくともそのような最適化のために、コンパイラを信頼し始める必要はありません!
"しかしいつもではない"

于 2010-06-10T20:23:58.587 に答える
1

私は、このスレッドの他の人が持っているように見えるこの慣行に強い嫌悪感を持っていないと言わざるを得ません。インライン化によるパフォーマンスの向上は、最も頻繁に使用されるケースを除いて、ごくわずかであることに同意します。(そして、はい、私実際にそのようなケースに遭遇しました。)私がこの種のインライン化を行う場合、私は便宜上、そして一般的にはこのようなワンライナーのためにそれを行います。ほとんどのユースケースでは、変更した場合にクライアント側での再コンパイルを回避する必要性はそれほど強くありません。

inlineはい、実装の配置によって暗示されるように、を削除できます。

また、アクセサーに対する猛威に少し驚いています。いくつかを吹き飛ばさずに、どのOO言語のクラスでもくしゃみをすることはほとんどできません。これらは、結局のところ、インターフェイスから実装を抽象化するための有効な手法であるため、オブジェクト指向の悪い習慣であると主張するのは少しマゾヒスティックです。アクセサーを無差別に書かないこと良いアドバイスですが、それらを根絶するための熱意に夢中にならないようにもアドバイスします。

それを取る、純粋主義者。:-)

于 2010-06-11T02:04:28.693 に答える