10

コンパイル時間が長くなることは別として、未使用のライブラリに対してリンクすることの欠点はありますか?

たとえば、次の2つの方法のいずれかでコンパイルされたプログラムの実行可能ファイルに違いはありますか。

g++ -o main main.cpp
g++ -o main main.cpp -llib1 -llib2 -llib3 -lmore

*mainをビルドするために実際にライブラリファイルは必要ありませんでした。

ファイルサイズは同じなので違いはないと思いますが、確認をお願いします。

4

4 に答える 4

14

場合によります。

  1. 、、、およびが静的ライブラリであり、それらからシンボルが使用されていない場合liblib1.a、違いはありません。liblib2.aliblib3.a

  2. 、、、またはが共有ライブラリである場合liblib1.so、それらが使用されているかどうかに関係なく、実行時にロードされます。リンカフラグを使用してこの動作を変更できます。このフラグをお勧めします。liblib2.soliblib3.so--as-needed

バイナリが実行時に直接ロードする共有ライブラリを確認するには、ELFシステムでを使用できますreadelf

$ cat main.c
int main()
{{
    0を返します。
}
$ gcc main.c
$ readelf -d a.out | grepが必要です
 0x0000000000000001(必要)共有ライブラリ:[libc.so.6]
$ gcc -lpng main.c
$ readelf -d a.out | grepが必要です
 0x0000000000000001(必要)共有ライブラリ:[libpng12.so.0]
 0x0000000000000001(必要)共有ライブラリ:[libc.so.6]

私のシステムでは、システムからのシンボルが実際に使用されているかどうかに関係なく、-lpngに対するリンクが表示されます。リンカフラグはこれを修正しますlibpng12.so.0--as-needed

$ gcc -Wl、--必要に応じて-lpng main.c
$ readelf -d a.out | grepが必要です
 0x0000000000000001(必要)共有ライブラリ:[libc.so.6]

ノート

  1. ライブラリの前--as-neededフラグを指定する必要があります。その後に表示されるライブラリにのみ影響します。だから動作しません。gcc -lpng -Wl,--as-needed

  2. このlddコマンドは、バイナリが直接リンクしているライブラリだけでなく、すべての間接的な依存関係も一覧表示します。これは、それらのライブラリがどのようにコンパイルされたかによって変わる可能性があります。readelf直接の依存関係のみがldd表示され、間接の依存関係のみが表示されます。

于 2012-12-21T04:44:06.357 に答える
0

静的ライブラリと共有ライブラリのどちらをリンクしているかによって異なります。静的ライブラリをリンクしている場合、実行可能ファイルのサイズは追加するたびに増加します。共有ライブラリにリンクしても、実行可能ファイルのサイズが大幅に増えることはなく、ライブラリシンボルのみが追加されます。

于 2012-12-21T04:45:51.787 に答える
0

はいぜったいに。欠点は、他の人(または将来的にはあなた)が何らかの理由でライブラリが必要であると想定することです。ほとんどの人は、プログラムの依存関係を整理するのに時間がかからないので、それらのリストはどんどん増えていきます。

コストはコンパイルされたコードとは関係ありませんが、プログラムの保守と移植に関係します。

于 2012-12-21T04:46:34.123 に答える
0

上記のいくつかの本当に良い答えがあります。さらに注意するのは、「それが実際にどのような違いをもたらすのか」です。メンテナンスのコストについてはすでに説明しました(たとえば、誰かがLib3を持たない新しいオペレーティングシステムをインストールする場合の問題。ユーザーはどこかでlib3を見つけてインストールする必要があります。また、lib3にはlib17も必要なので、あなたもそうではありません。インストールすると、ユーザーの作業が増えます)。

ただし、バイナリをロードするときに、実際に使用されていない共有ライブラリに対してリンクしている場合でも、システムはそれらのライブラリを探し、存在しない場合はロードを拒否します。これにより時間が追加され、悪夢がインストールされます。 。

コードがロードされると、追加の実行時ペナルティは発生しません。

そうは言っても、未使用のライブラリに対してリンクすることについての議論がある場合があります。コードにオプションUSE_FOOがあり、FOO機能がビルド時の任意の選択に基づいてのみ含まれているとします(たとえば、「これはLinuxカーネル> 3.0であるか」、「システムに豪華なグラフィックカードがありますか」)。FOOはLib1を使用します。ビジネスを行うために、USE_FOOが設定されていないときに実際には必要ない場合でも、ビルドシステム(makefileなど)を常にlib1に対してリンクするのを少し簡単にすることができます。

ただし、一般的に、不要なライブラリに対してリンクしないでください。それはより多くの依存関係を引き起こします、そしてそれは決して良いことではありません。

于 2012-12-21T10:18:44.870 に答える