Goは、Javaと同じ微妙なメモリリークの影響を受けますか?


91

ここに事実があります:

  • Goという言語にはガベージコレクターがあります。

  • Javaにはガベージコレクションがあります

  • 多くのJavaプログラムには(微妙かどうかにかかわらず)メモリリークがあります

メモリリークがあるJavaプログラムの例として(気弱な人のためではなく、質問があなたの信念を揺るがすかもしれません)、「リークを見つける」ボタンさえあるTomcatと呼ばれる小さなJavaプログラムについてここを見てください:方法はありますかTomcatでのアンデプロイメントメモリリークを回避するには?

だから私は疑問に思っています:Goで書かれたプログラムは、Javaで書かれたいくつかのプログラムが示すのと同じ種類の(微妙かどうかにかかわらず)メモリリークを示しますか?


29
「多くのJavaプログラムには(微妙かどうかにかかわらず)メモリリークがあります」この「事実」の証拠はありますか、それとも単なる論点ですか。
Peter Lawrey 2010

17
@Webinator:「多くの」Javaプログラムが持つこれらの「微妙なメモリリーク」の1つの例を示す必要があると思います。ガベージコレクターのバグを主張しない限り、純粋なJavaでメモリリークを発生させる唯一の方法は、使用しなくなった参照を保持することです。たとえば、オブジェクトをコレクションに入れ、そのコレクションからオブジェクトを削除しないことです。これがあなたが言及している種類のリークである場合、Goを含め、世界中のどの言語もそれらから保護しません。
JeremyP 2010

14
ここで私が話していたメモリリークしている(200 upvotes、150 upvotesとの回答は、実際のJavaメモリリークの多くは説明):stackoverflow.com/questions/6470651/...
SyntaxT3rr0r

6
もちろん、JAVAプログラムにはメモリリークがあります。ドットが必要になったときに、参照をnullに設定するのを忘れてください。オブザーバーデザインパターンまたはスレッドローカル変数を使用して、大規模な永続コレクション(キャッシュなど)で頻繁に発生します。これは理論的ではありません。本番環境でいくつかのメモリリークを自分で修正しました。そして、これは反Javaではありません。私は5年以上フルタイムのJAVA開発者であり、さまざまなプロジェクトに取り組んできました。JAVA(または他のすべての既存の言語)でメモリリークが発生する可能性があることを認識しないでください。これはファンボイズムではなく、実際にどのように機能するかを理解していないことです。
Nicolas Bousquet 2011

6
この質問は、「ファンボイズム」、「誰かの信念を揺るがす」などについてのドラマやコメントなしで行うことができます。Esp。議論全体が「私の定義はmemory leakあなたの定義よりも優れている」に要約されるからです。
–LAFKは2017

回答:


44

ここでは、さまざまなタイプのメモリリークを混乱させています。

凶悪な明示的メモリ管理ベースのメモリリークは、Java(または他のGCベースの言語)ではなくなりました。これらのリークは、未使用としてマークせずにメモリのチャンクへのアクセスを完全に失うことによって発生します。

コンピュータが私たちの心を読み取ることができるまで、Javaや地球上の他のすべての言語にまだ存在する「メモリリーク」はまだ私たちのそばにあり、予見可能な将来になります。これらのリークは、コード/プログラマーが技術的に不要になったオブジェクトへの参照を保持していることが原因です。これらは基本的に論理的なバグであり、現在のテクノロジーを使用してどの言語でも防ぐことはできません。


23
メモリリークは、単にメモリを解放するのを忘れた場合です。Javaでは、これは参照をnullに設定するのを忘れたときに発生します。C ++では、無料通話を忘れた場合に発生します。どちらも有効なメモリリークのケースです。そして基本的な問題は同じです。プログラムが最終的にOutOfMemoryエラーでクラッシュするまで、プログラムはますます多くのメモリを消費します。
Nicolas Bousquet 2011

1
プログラマーがそのような論理エラーを起こすのを防ぐ言語がないことは事実ですが、Java SDK自体にそのようなエラーがいくつか存在することも事実です(たとえば、構築されるすべてのそのようなオブジェクトがjava.util.logging.Level含まれるプライベート静的を含むを参照してください)。ArrayList構築に配置され、それらが削除されることはありません)、Javaをプログラミングするときに、そのような欠陥を含まない他の言語よりも回避するのが難しくなります
Jules

7
OPは、リンクされた質問の受け入れられた回答のように、実際には到達できないオブジェクトのメモリリークについて質問していたと思います。スレッドからのクラスのロードによって引き起こされるメモリリーク。-1
qbt937 2014

1
また、静的分析によって、参照がその有用な寿命を超えて存在し続けるかどうかを判断できる可能性も考えられます。
カイルストランド

1
@Amritいいえ、あなたはないガベージコレクタの収集メモリではないもはやへの参照を持っています。まだ参照しているものを削除してもよいかどうかを知る方法はありません。
ラファエルシュミッツ

19

Goプログラムでメモリリークが発生する可能性が非常に高くなります。Goの現在の実装には、単純なマークアンドスイープガベージコレクターがあります。これは一時的な解決策としてのみ意図されており、長期的なガベージコレクターとして意図されていません。詳細については、このページを参照してください。ヘッダーの下を見てくださいGo Garbage Collector。そのページには、現在のバージョンのコードへのリンクもあります。


1
Javaのマークアンドスイープコレクターの問題の1つは、メモリの断片化です。技術的にはメモリではありませんが、アプリケーションで使用できるメモリが失われる可能性があります。
Peter Lawrey 2010

9

「メモリリーク」とは、プログラマが解放されると考えていたメモリの一部が解放されない場合です。これは、ガベージコレクションの有無にかかわらず、どの言語でも発生する可能性があります。GC言語の通常の原因は、メモリへの追加の参照を保持することです。

「言語はメモリリークを引き起こしません、プログラマーはメモリリークを引き起こします」。


8

ガベージコレクションの有無にかかわらず、ほとんどの場合、Java、Go、またはその他の言語でメモリリークが発生するプログラムを作成できます。

ガベージコレクションはプログラマーの負担の一部を取り除きますが、リークを完全に防ぐことはできません。


4
分かった分かった。具体的には、Javaに存在するちょっと微妙なメモリリークについて話します。タフなJavaでさえ、当初は、GCのおかげでメモリリークが存在しない言語として販売されていました。
SyntaxT3rr0r 2010

4
申し訳ありませんが、それは明確ではありませんでした。「多くのJavaプログラムには(微妙かどうかにかかわらず)メモリリークがあります」とおっしゃいました。
jzd 2010

3

ここでは抽象化レベルを混合しています。メモリリークは、ライブラリのバグが原因です(オブジェクトは、「aのチェーンはbへの参照を保持しますが、オブジェクトは相互に参照します」と、ガベージコレクタの実装における効率と正確さ。そのようなループを見つけるためにどのくらいの時間を費やしたいですか?2倍の時間を費やすと、2倍の長さのループを検出できるようになります。

したがって、メモリリークの問題はプログラミング言語固有のものではなく、GO自体がJavaよりも優れている、または劣っているという理由はありません。


1
私は完全には同意しません。メモリリークは、Javaが自分の足を撃つことを可能にするという事実によるものであり、必ずしもライブラリのバグとは関係ありません。多くのプログラマーは、Javaのメモリーをゆっくりと、しかし確実にリークするプログラムを作成します。これは、ライブラリーのせいではなく、彼ら自身のせいです。また、正確にJava GCが時間/リークの可能性のトレードオフを行っている場合、Goも同じトレードオフを行っていますか?
SyntaxT3rr0r 2010

1
問題は、「そのようなループを見つけるのにどれだけの時間を費やしたいのか」ということではありません。 質問は「スペックがGoGCがそのようなループに費やす時間をどのくらいの時間にするか」であり、これはIMHOが興味深い質問です。
SyntaxT3rr0r 2010

16
循環参照チェーンは、Javaでのガベージコレクションを妨げません。
アンディトーマス
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.