アカウント名:
パスワード:
別に擁護するほどの義理も思い入れもないんだけど。
僕がJavaで駄目だと思うところはまず実行速度です。 JITの技術がありますが本質的な解決策では無いと思います。 しかもテキスト処理なんかはJITを使ってもAwkよりもPerlよりも遅い。
必要な時にプロセスとして起動するような用途には当然向かないですよ? PerlはともかくAWKを並べてるところを見ると、「テキスト処理」ってUNIXのフィルタプログラム的な使い方を想定してるんじゃないでしょうか?
Javaのソフトウェアをまともに使おうと思ったら、JavaVMは基本的に立ち上げっぱなし、その中でサービスを回して行くような方法しか今のところはないでしょう。それが、いわゆるJ2EEの考え方(のごく一面)ですね。
だからこそ、JavaOSなんて考え方があったんでしょう。要は適材適所ってこと。
awkやperlに比べて不利な点は、 「実行速度が遅い」ことではなく、「起動が遅い」ことではないでしょうか。
一回走り出したら、十分な速度を持っているよーな気が。
ぼくは、ポインタとはまったく別に「参照」というものを理解している人がいたら、そっちのほうに軍配を上げたいです。
C だって「解放忘れ」なら同じ現象が起こるでしょー。
Java は free を呼ぶ替わりに使わなくなったポインタに逐一 null を入れろ、ってだけ。
C でこれと同じ状況は「解放忘れ」で簡単に起こる、というだけのことだろう。
> > Java は free を呼ぶ替わりに使わなくなったポインタに逐一 null を入れろ、ってだけ。 > これも、ガベージコレクタがオブジェクトを回収する際の「ヒント」を与えるために使われるテクニックであって、必ずしなければならない、というものではありません。 一般論ではもちろんそうだが、 メモリ不足でVMが落ちる、なんて状況では必須だろう (そうでなければGCが回収しているはずなんだから)。
isualC++のメモリリーク警告って静的になめて出すだけなんでしょうか?それとも動的に解析してくれる?
GCを利点として挙げる人がいますが、それも僕はどうかと思っています。 GCがあるためにむちゃくちゃなプログラムでもある程度動いてしまいます。
C++ でマルチスレッドプログラムを書く時のメモリ管理の難しさといったら。まあ,気にしなくても動きますけど(皮肉なことに)。
いいえ。G7さんが紹介してくれましたURLがよい資料なので、詳しくは そちらを見てください。ここでは簡単に言いますと、GCは古典的には、
確認ですが、
Java の Heap に関しては、激しくオブジェクトの生成/回収を繰り返してもフラグメンテーションによって新規オブジェクトが生成できない、とゆー事態には陥ったことがない
というのは、異なるサイズのオブジェクトを生成、回収した場合ですか? というのは、同じサイズばっかりだったらそもそも空きメモリの断片化は問題にならないはずなので。
ちなみに、アドレス空間を長持ちさせると(Unixのkernelはその典型)、オブジェクトの生成にともなう再初期化が大きなオーバヘッドになってきます。これは、オブジェクトが不要になった時、その中身はオブジェクトが初めて生成された時とほぼ同じになっていることが多いためです(eg 連結リストの要素の場合、前後へのポインタは初期化時も解放時もnull)。
これを解決する方法として、解放されたばかりのオブジェクトを直ちに再利用に回すことが挙げられます。Solarisのslab allocatorはこの方法を用い、オブジェクトの割り当てと初期化時間を最大で8割減らすことができています。Javaでもこういうことはやってるんでしょうか?
それ、もしかして、解放された領域を、「同じ種類」ごとに別々のフリーリストにぶら下げたりする、んでしょうか?
厳密には、page level allocator(つまりvirtual memory)から切り出してきた、free objectのcacheに放り込みます。このcacheはper object typeです。
だとしたら、種類という概念がクラスのおかげ(乱暴な言いかただが)でC的世界よりずっとはっきりしているoop処理系においては、より旨くやれるんではないでしょうか?
それはなんともいえません。Uresh Vahaliaは著書Unix Internals: The New Frontiers [amazon.com]の中で、以下のようなslab allocatorの欠点を指摘しています(以下は邦訳より)。
スラブ・アロケータの1つの欠点は、それぞれのオブジェクトの種類に対してことなるキャッシュを持つことに起因する、管理上のオーバヘッドである。 (中略) (キャッシュに含まれる)要素が少なく、あまり使用されないキャッシュの場合のオーバヘッドは、しばしば、無視できないものである。
となると、cacheを使うか否かを決める問題が生じます。Solarisの場合、私が本や実装を(誰か1994年夏のUsenix [usenix.org]予稿集持ってませんか?)見た限りでは、cacheを使うか否かはobject type毎にhardcodeされている(すなわち人間が決めている)ようです。Unix kernelならこれでも何とかなりますが、個々のプログラムを支える枠組み、すなわち言語処理系やruntime libraryなどの場合は機械的に決めないと使いものにならないでしょう。Solarisがこれをやっていないということは、機械的な決定は難しいということでしょうか。
> GCがあるためにむちゃくちゃなプログラムでもある程度動いてしまいます。 これは、null なのに使おうとしたって事で、C++とJavaに差は余り無い気がします。 GCとは関係ないのでは?
> 1時間ぐらいだったら動くけど長時間動かしているとVMが落ちることがありますし、その時のバグを見つけるのが非常に大変です。
より多くのコメントがこの議論にあるかもしれませんが、JavaScriptが有効ではない環境を使用している場合、クラシックなコメントシステム(D1)に設定を変更する必要があります。
犯人は巨人ファンでA型で眼鏡をかけている -- あるハッカー
Javaの必要性 (スコア:1)
僕はいまいちJavaの良さが分かりません。
誰かJavaのすばらしさを語ってもらえないでしょうか。
Re:Javaの必要性 (スコア:1)
Java Applet のことだったり、 JavaScript のことだったりする
ことがあるので、いっかい問い詰めてみたほうがいいです。
Re:Javaの必要性 (スコア:2, 参考になる)
JITの技術がありますが本質的な解決策では無いと思います。
しかもテキスト処理なんかはJITを使ってもAwkよりもPerlよりも遅い。
次に移植性です。
Write Once Run Anywareとか言っていますがはっきり言って実現されて無いと思います。
移植性 + 速度
で考えるとCの方が上だと思っています。
GCを利点として挙げる人がいますが、それも僕はどうかと思っています。
GCがあるためにむちゃくちゃなプログラムでもある程度動いてしまいます。
1時間ぐらいだったら動くけど長時間動かしているとVMが落ちることがありますし、その時のバグを見つけるのが非常に大変です。
最後にIDEです。
デバッグが難しいのにろくなIDEが無いために開発が非常に面倒です。
後は思想的な話ですが、そもそもJavaが出てきた時のライセンスが僕は嫌いでした。
「全ての環境で同じプログラムが動く。だからうちにお金を払ってね。」
って思いっきり某社の戦略ですよね。
今はライセンスが変わりましたが、それは単にJavaが最初のライセンスではやらなかったから変えただけであって、根本的な思想は某社と大して変わらない気がします。
dan kamiyubiさんの意見をお聞かせ下さい。
長文失礼しました。
Re:Javaの必要性 (スコア:3, 参考になる)
方の話をすると、
まず実行速度ですが、私の作ってるようなものだと他の要素、通信やデータベー
スが遅いので、今Javaな部分をCで書いたところで数%も速くならない、むしろ
開発速度が重要で、そういう意味では perl,python,ruby などの方が向いてる
と思います。
遅けりゃ負荷分散したらいいやん、ということで最近ではPCクラスタで分散オ
ブジェクトとかすることが多いので、言語標準のライブラリで分散オブジェク
トがしやすいのもありがたいです。
移植性は、Cでは移植性のないコードも書き易いのでその点さすがにC以外の方
がいいのでは。私の知るヘボCプログラマはすぐにリトルエンディアンを前提
にコードを書くのでSPARCにもってくとき苦労しました。
GCだめだからJavaだめってのは何とも…。他のオブジェクトを明示的に解放し
ない言語もだめなんでしょうか。
IDEは確かにあったほうが参入障壁は低いですね。初心者に勧め易いというか。
私のほうでは必要ないので、無いことがデメリットにはなりません。Junitを
使い出してからはいわゆるIDEでデバッグはしたことないです。バグがあった
らまず再現性を出すテストを書きます。Javaは例外時スタックトレースが出る
のでそれで分かることも多いです。あと再現性のだしづらいバグではIDE のあ
り無しはデバグの容易さとは関係ありません。GUIだと例えばマウスを押して
から離すまでの間動くコードのデバグなどはIDEがあっても楽にはなりません。
思想的な話は良く分からないのでパス。まあ、まっとうなソフトウェア技術者
ならC/C++、perl、python、java、lisp くらいは書けて当然なので「要は適材
的所だ」で済むのではないでしょうか。
Re:Javaの必要性 (スコア:1)
「Javaが適材適所の言語である」というのは納得してます。
でも、僕が良く分からないのは適材適所で無いような気がする分野にまでJavaが持ち込まれているような気がします。
例えばReal Time Javaなんていうのは本当に必要なのでしょうか。
dan kamiyubiさんはおそらくJava信者では無いと思いますが、Java信者の人はよく「Java万能」と考えていることがあります。
dan kamiyubiさんの目からみてJavaの可能性はどの程度あると思いますか?
Re:Javaの必要性 (スコア:1)
Java 万能 (スコア:1)
(100% Pure Java にこだわると)Java 言語では
(まともな) JavaVM が書けないのですから、、、
p.s.
任意のアドレスに任意の型でデータを読み書きできる
バイトコードのプリミティブがあれば、比較的まともな
速度で動く JavaVM が Java で書けるのです。
そういうプリミティブがない場合は、しょうがないので
ヒープ空間全体を覆うような強大な byte 型配列をとって、
bastore と baload でちまちま読み込んで論理合成する
しかない!?
コンタミは発見の母
Re:Javaの必要性 (スコア:1)
オフトピですが、javaが、delphiくらいに
「property」と「metaclass」の機能を持っていれば、
もっとRADをエレガントに作れただろうに、と
ちょっと残念に思っているところです。
まぁJ++とかC#とかいう声もあるが(笑)、MS専用じゃあ、ちょっとね…
delphiみたいに、強型で静的な言語であることと、
RADに(ほかにも)役立つような動的性を持たせることとが、
両立する言語ってのを作ることができるのは事実なわけで、
それをやらなかったjavaってのが、なんともねえ。
beanの仕様はborlandの協力のもと作ったそうですが、
propertyもなにも無くコーディング規約(^^;で実現されるbean
ってやつは、とても半端な代物に見えますし、
クラスメソッドの多態ができないことによって
たとえばClass#newInstance()が「引数のないconstructorしか呼べない」
などという間抜けな制限があるわけで、
borland側はさぞかし歯痒かったのではなかろうかと想像します…。
#てゆーかnewInstanceはライブラリレベルの単純ミスでもあるなあ。
#Method#invokeみたいに引数を配列かなんかで渡すことにすれば良かったのになあ…
Re:Javaの必要性 (スコア:2, 興味深い)
別に擁護するほどの義理も思い入れもないんだけど。
必要な時にプロセスとして起動するような用途には当然向かないですよ? PerlはともかくAWKを並べてるところを見ると、「テキスト処理」ってUNIXのフィルタプログラム的な使い方を想定してるんじゃないでしょうか?
Javaのソフトウェアをまともに使おうと思ったら、JavaVMは基本的に立ち上げっぱなし、その中でサービスを回して行くような方法しか今のところはないでしょう。それが、いわゆるJ2EEの考え方(のごく一面)ですね。
だからこそ、JavaOSなんて考え方があったんでしょう。要は適材適所ってこと。
Re:Javaの必要性 (スコア:2, 参考になる)
それは実感しますね。
jvmの起動はやっぱり遅い。一方でいったん上がれば遅さが気になることは案外(?)多くない。
複数の関連ある処理(の単位:OOPとそれ以外を比較するときにはこの辺が曖昧な言い方になっちゃいますが)を
繋ぎあわせて使うという状況においては、unixのプロセスモデルより、java(に限らないけど)の
Object単位のモデルのほうが、メリットが多いことが多いです。プロセスだと処理単位間の「壁」が高すぎ。
それがまさに、CGIに対するservlet、makeに対するant、のメリットになっているという触れ込み(^^;。
オフトピだけどant。make時に必要な複数の処理を同一プロセス(^^;でやってくれるのは
たしかに魅力的なんだけど、もう一歩欲しいです。
もしコンパイルが「終わって」も尚プロセスが残っていてくれたら、そして
次のコンパイルにそれを使い回せたら、きっと更に速くなるだろうに、と。
Re:Javaの必要性 (スコア:1)
AWK、Perlを例に挙げたのはUNIXのフィルタプログラム的な使い方を想定してるわけではなく、とにかく遅いって言いたかっただけです。
僕自身AwkやPerlよりも遅いと知ったときに非常に驚いたもので。
「ある特定の用途にはJavaが非常に有用だ」
というのは分かります。
ただ、言語として総合的な観点から見た場合に魅力的な言語だと僕は思えません。
しかし、Java信者ってすごく熱烈的ですよね?
いったいどこに魅力を感じるのかというのが僕にとって興味あることなのです。
Re:Javaの必要性 (スコア:1)
"あーんなに遅いのに、みんな平気で使っているんだろうか?"
って Java を使うときはいつも思っていたのですが、
やっぱしそのように思っている同士がいたということで。
Java の情報って、"けっこう速いですよ、いいですよ"
って思わせる情報ばっかりが見つかって,
"Java ダメじゃん.." って情報はあまり書いている人が
多くないんですよね。
欠点を述べるのって、結構重要だと思うのですよ。
だって、どのような時に Java を使えばいいかという
判断材料としては非常に有効ですから。
いろいろ勉強になりました。
Re:Javaの必要性 (スコア:1)
もちろん実行系の制約ってのは、Javaの思想に起因してるのだろうけど、それは言語としての評価とはちょっと違うように思います。
確かに、環境(言語と実行系を両方含めた話)としてのJavaは、あれこれ不満が多いですけど、ね。
Re:Javaの必要性 (スコア:1)
もちろん「言語」という言葉をそんな厳密に使ってるわけじゃないのはわかってるのです。けど、つい血が騒ぐというかなんというか。
Re:Javaの必要性 (スコア:1)
awkやperlに比べて不利な点は、 「実行速度が遅い」ことではなく、「起動が遅い」ことではないでしょうか。
一回走り出したら、十分な速度を持っているよーな気が。
# emacsみたいにdumpして(比較的)高速に起動するということはできないのだろうか…。Re:Javaの必要性 (スコア:1)
instance(ってのかな)をメモリからファイルに永続化しといて
それを後で読みなおして再現する、って奴ですよね。
smalltalkだとImageFileとか言うんだっけか?
javaでは、class fileを束ねる(束ねるだけだ)ためにはjarフォーマットが有りますが、
そういやinstanceを束ねる標準フォーマットってのは作られなかったですよね。
objectを直列化する仕組とかは有るけど、それの最初の応用例(^^;としての
永続標準フォーマットってのは…
たしかに、勿体ない話です。
Re:Javaの必要性 (スコア:1)
どういうときにどう遅いか?という話しかたをしないと、
それこそ不毛な議論になっちゃうのでわ(^^;。
さすがにどんな状況でも必ず遅いというわけではないのですから、
「とにかく」では大雑把すぎです。
ま、今ここでベンチマークやって具体的な結論を出せ、とまでは迫りませんが、
今じゃなく実際になんらかの選択をする場面になったときには、
「とにかく」じゃなくてもう少し情報量のある思考を、してください。
そのほうが世のためですから。
#前述のように、状況を「区別せず差別する」のは不味いわけです(^^;
#どういう状況なのか?を、しっかりと"見る"必要は、ありますね。
>「ある特定の用途にはJavaが非常に有用だ」
>というのは分かります。
>ただ、言語として総合的な観点から見た場合に魅力的な言語だと僕は思えません。
総合といっても、(あなたが意図するところの)総合とは何処から何処までを指すのか?ってのが問題でしょうね。
たとえばunixフィルタ的に使う限り常(^^;に遅いであろうわけですが、
それは総合というよりもunixという特殊な(^^;状況における特殊解であるわけです。
そういう特殊な状況では、不運にも(^^;javaはperlより遅くなってしまう、と。
ならば、そういう状況に出逢ったとき、じゃあjavaをやめる、という選択肢と同じくらいに、
じゃあunixをやめる、という選択肢だって、ひょっとしたら考慮に値するかも知れない。
普遍であるかのように思っていた状況が、実は結構ローカルなものである、ってことは、よくあるようです。
どうか、お見知り置きを。
それはそれとして、俺も、javaにゃ納得できない面が結構あります(^^;;;;
Re:Javaの必要性 (スコア:2, 興味深い)
不要なオブジェクトへの活きた参照をいつまでもかかえてしまうようなコーディングをしてしまうと,長時間運用後にVMが落ちることがあります.確かに見つけにくいバグではありますが,GCがない場合のメモリリークはそれ以上に見つけにくいバグですし,何よりも開放してしまったメモリ領域を触る危険性がない方が安心して使えるのではないでしょうか.
Re:Javaの必要性 (スコア:1)
それともぼくが用語の定義を間違えているのかな。このあたりの概念、感覚的にしか把握していません。
Perl より遅くなる理由はない、というのは理解できますが。
// ただ、 Perl と実行速度を比較されているのは Java がなんか気の毒。
鵜呑みにしてみる?
ポインタ(Re:Javaの必要性) (スコア:1)
// なお、ぼくは C/C++ を学んだ後でしか Java や Visual Basic を理解できませんでした。
同様に、Cのポインタをアドレスとはまったく別に理解している人がいたら、そっちのほうがすごいと思いますが、いないだろうなあ……。
// ぼくはアセンブリ言語を学んだ後でしか C を理解できませんでした。これはある面恥ずかしいかも。
なお、ぼくはプログラマではありません。
鵜呑みにしてみる?
Re:ポインタ(Re:Javaの必要性) (スコア:1)
-----------------
#そんなワタシはOS/2ユーザー:-)
Re:ポインタ(Re:Javaの必要性) (スコア:1)
俺はたまたま(^^;初めて出逢った参照の機能が明示的に使える言語がCだったんで、
Cの理解から入りましたが、そんなにベッタリとメモリメモリとは勘がえてなかったような
気がするなあ。
俺はたしかちょうどK&R2和訳が出始めたころだったかな。
で、たしか(^^;あれって、メモリのアドレスを全然抽象化せずに具体物として理解しろなどとは
どこにも書いてなかったようにしか記憶していないんですけど…。
オブジェクトとか、領域とか、そういう抽象的な理解で良いわけですよね。
あとはせいぜい、領域間の「連続」性という概念が有るかどうか。
Cにはこれが有るんで、逆にいえばバッファオーバーランをやってくれる(笑)。
ポインタ(や一般的に参照)自体は、難しいと思ったことは無いなあ。
なんでもかんでも目の前に即値が無いとおちつかない人ってのを見てると
憐れを感じたものだったなあ(笑)。
そんな俺はWiki大好き。あれは参照まみれだからね(^^;
とこで、参照が難しいと思ってる人って、もしかして教科書が悪かったんじゃないかな?
たまにあるよね、変に実際のメモリアドレスに拘泥した説明ばかりする
(そうするほうが易しいと決めつけてる)ような参考書ってやつが。
あんなことするから却って混乱するんじゃないかな?
Re:ポインタ(Re:Javaの必要性) (スコア:1)
ということは、ほかにも「参照」はあるけどポインタっぽくない言語というのはたくさんあるのでしょうね。不覚。
鵜呑みにしてみる?
Re:Javaの必要性 (スコア:2, 参考になる)
> GCがあるためにむちゃくちゃなプログラムでもある程度動いてしまいます。
> 1時間ぐらいだったら動くけど長時間動かしているとVMが落ちることがありますし、その時のバグを見つけるのが非常に大変です。
C だって「解放忘れ」なら同じ現象が起こるでしょー。
Java は free を呼ぶ替わりに使わなくなったポインタに逐一 null を入れろ、ってだけ。
むしろ、C では使われていないポインタに NULL 以外の値が
入っていることがあって、そっちの方が危ないと思うのだがどうか。
#ま、C だって boehm GC みたいなのがあるけどね。
# mishimaは本田透先生を熱烈に応援しています
Re:Javaの必要性 (スコア:2, 参考になる)
Cで動的に確保されたメモリブロックは、明示的に解放しない限り、(少なくとも)そのプロセスの生存中は回収されないのに対して、Javaの場合は、他から参照されなくなったオブジェクトは、ガベージコレクタによって自動的に回収されます。(そもそも、解放するという操作自体がない)
また、 これも、ガベージコレクタがオブジェクトを回収する際の「ヒント」を与えるために使われるテクニックであって、必ずしなければならない、というものではありません。(スコープを外れ、どこからも参照されていなければ、回収される)
# 「ポインタ」という用語も不適切かと。
(未確認ですが、ガベージコレクタの性能の向上で、そういったテクニックをする必要もなくなってきた、というような話もあるらしいです)
Re:Javaの必要性 (スコア:1)
> > C だって「解放忘れ」なら同じ現象が起こるでしょー。
> 少し違うと思います。
> Cで動的に確保されたメモリブロックは、明示的に解放しない限り、(少なくとも)そのプロセスの生存中は回収されないのに対して、Javaの場合は、他から参照されなくなったオブジェクトは、ガベージコレクタによって自動的に回収されます。(そもそも、解放するという操作自体がない)
?よく意味が分からん。
短時間では問題はないが、長時間動かすとVMが落ちるようなプログラム、
というのは明らかにメモリを食い潰しているのであって、
C でこれと同じ状況は「解放忘れ」で簡単に起こる、というだけのことだろう。
> > Java は free を呼ぶ替わりに使わなくなったポインタに逐一 null を入れろ、ってだけ。
> これも、ガベージコレクタがオブジェクトを回収する際の「ヒント」を与えるために使われるテクニックであって、必ずしなければならない、というものではありません。
一般論ではもちろんそうだが、
メモリ不足でVMが落ちる、なんて状況では必須だろう
(そうでなければGCが回収しているはずなんだから)。
#「ポインタ」は不適切だったな。すまん
# mishimaは本田透先生を熱烈に応援しています
Re:Javaの必要性 (スコア:1)
オブジェクト同士の意図しない循環参照などを断ち切る(その結果ガベージコレクタが回収できるようにする)ためにnullを代入すべきだということであれば同意します。
が、Cでfreeを呼ぶ代わりに、Javaではとにかくnullを代入すればよいという風に読めたので。それだと、Cのメモリ管理のやり方とJavaのやり方を混同されかねないと思いました。
結果的に同じことじゃないかといわれそうですが、解放が(プログラムの指示によって)能動的に行われるか、(VMの働きによって、プログラム側から見ると)受動的に行われるかという概念の違いは大きいのではないかと思います。
Re:Javaの必要性 (スコア:1)
という事でしょうか。
サーバー側のJavaが花開いたのは、バックエンドがころころ
変わるのに対応出来る、という事なのでは。
-----------------
#そんなワタシはOS/2ユーザー:-)
どの機能についていっています? (スコア:1)
これってどの機能のことを指していますか?
VC6.0を日常業務に使っていますけど、VC がメモリの解放し忘れ
を指摘してくれたことなど皆無なのですけど、、、
あとデバッガがメモリリークを指摘する機能は 設計がよくでき
ていてちゃんとコーディングされたプログラムに対して行う場合は
有効だけど、いい加減な設計のプログラムに対しては無力だと
思います。
#「ほとんどメモリは使い捨て」の前提で書かれた20万行ぐらいの
#プログラムを NuMega の BoundsChecker に掛けたら数千箇所も
#問題を指摘されてことがある、、、
コンタミは発見の母
BoundsCheckerは、Visual C++とは別製品だよ (スコア:2, 参考になる)
BoundsCheckerは、元々米国のNumega社が開発し、米国Compuware社に買収されて、現在は「Compuware社のNumega製品」ということで販売されています。
私の知る限りでは、M$社にぴったりくっついていて、VC++などとの相性というか、一部のように機能する、ということを売りにしていますが、完全な別会社の別製品です!。
ご参考までに日本コンピュウェアの該当サイトをお知らせしておきます。
ここ [numegajapan.com]です。
この会社の営業やってる知り合いに教えてやろうかと思っちまったい!
Re:どの機能についていっています? (スコア:1)
#63080 の人のメモリ解放のし忘れ検出の機能はこれみたいですね。
これは new して delete されていないものを表示するだけだから、
メモリリークをしている可能性のある箇所を大量表示しちゃうんで
すよね。
ないよりましだけど、本当にメモリリークを潰す必要があるプログラム
(終了のこないサーバープログラムや、プログラムの途中のフェーズ
で大量にメモリが必要になるプログラム)には 使えんです。
コンタミは発見の母
BoundsChecker (スコア:1)
ランタイムベースの非常に強力なエラー検出ツールです。
配列の境界を越えたアクセスをチェックしてくれるのが名前の
由来だと思います。
今はもう持っていないので詳細をチェックできませんが、メモリ
リークやリソースリーク、配列・構造体の境界チェック、ダング
リングポインタの検出ができたはずです。
似たようなツールに Rational 社の purify があります。
コンタミは発見の母
Re:BoundsCheckerは、Visual C++とは別製品だよ (スコア:1)
ええと。VCのことは知りませんが、一般的にいえば
そういうのはプラグインという類のものであって、
わざわざ「完全な別会社の別製品」などと言うほどのことでもないと思うんですが。
プラグインならばどこの馬の骨にも作ることはできるので。
そして妥当なプラグインAPI(もし有るならば)に則って作ったプラグインは、
相性ピッタリでも全然変な(珍しい)話では、ないわけで。
一部のように機能するってのもプラグインならば当然のことですし。
#プログラムすなわちos上に直接乗るアプリケーション、だと思っていませんか?
その製品がどうなのかは知りませんが、たしかVCにもプラグインみたいな概念は
有るんじゃありませんでしたっけ?
#delphiにもjbuilderにも有るよね(^^;
え?windowsのプラグインのIE? うーん(^^;;
Re:Javaの必要性 (スコア:1)
前者だったら、ワタシはむしろプログラムする人がタコい気がしますし、後者だったらこれはチューリング賞クラスの偉大な機能な気がしますが、どっちなのでしょうか?
-----------------
#そんなワタシはOS/2ユーザー:-)
Re:Javaの必要性 (スコア:1)
ぐわ、VisulaC++のIDEが行う動的チェックってただのスタックチェックなのね。IDEが静的なソースから動的にフローを出してくれてそれでメモリリークを教えてくれるのかと思いましたよ。
pascalerとしてはまったく不要の機能だなぁ・・・
-----------------
#そんなワタシはOS/2ユーザー:-)
GCの必要性 (スコア:2, 参考になる)
C++ でマルチスレッドプログラムを書く時のメモリ管理の難しさといったら。まあ,気にしなくても動きますけど(皮肉なことに)。
Re:GCの必要性 (スコア:1)
>テーションを防ぐためのものと考えれば,その恩恵は計り知れないと思います。
え?
http://www.is.s.u-tokyo.ac.jp/~vu/jugyo/processor/process/soft/compilerresume/gc/gc.html
>Copying GCの興味深い性質は、コピーするときにオブジェクトの空きをつめるため、fragmentationが発生しないということである。
によると、フラグメンテーションを無くす機能(つーか嬉しい副作用?)を期待できるかどうかは
GCのアルゴリズム次第であって、GC一般の性質ではない、と読めますけど?
それとも、その副作用のあるGCしか使う予定が無い、言い換えれば
使おうとしている処理系のGCがお望みのアルゴリズムであることが既に判っている、
という状況なのでしょうか?
そりゃそうと、メモリリークが無くなるってのについては、有り難いと思いますよ。
1:unixプロセスモデル配下の短寿命プロセスならば、最悪でも「間もなく」OSがメモリを回収してくれる
ので有り難味は少ないかもだが、そうでないならそれ以外の管理が必要になる。
2:開放タイミングを決定するのが結構面倒なプログラミング形態も、ある。
ので、あーゆーものは、(プログラマの技量次第というよりも(笑))状況次第で、凄く欲しくなると思うんですが。
Re:GCの必要性 (スコア:1)
(中略)
> フラグメンテーションを無くす機能(つーか嬉しい副作用?)を期待できるか
> どうかは GCのアルゴリズム次第であって、GC一般の性質ではない、と読め
> ますけど?
元コメントは、フラグメンテーションがプログラマに不可視になることを言いたかったんだと、愚考します。
# 違ったらどうしよう。^_^;
新しいjavaコマンド(VM)は並列GCを実装していますね。どんなアルゴリズムを使ってるんでしょうか。興味があります。106CPUでもちゃんと動いてくれるでしょうか。:-)
Re:GCの必要性 (スコア:1)
> GCのアルゴリズム次第であって、GC一般の性質ではない、と読めますけど?
GC がどのようなアルゴリズムで行われるにせよ、compaction は
行われてるのではないでしょうか? compaction されるというこ
とは、その時点でフラグメンテーションも解消される、ということ
ですよね?違う?
Java の Heap に関しては、激しくオブジェクトの生成/回収を
繰り返してもフラグメンテーションによって新規オブジェクトが
生成できない、とゆー事態には陥ったことがないため漠然とそう
思ってたんですけど…。
UNIX のようにプロセスを起こすコストが結構大きい OS がサーバ
で主流な昨今、比較的容易にお行儀のいい長寿命プロセスを作成
出来る Java は非常に有用だと思います。
Only Jav^Hpanese available :-)
Re:GCの必要性 (スコア:1)
いいえ。G7さんが紹介してくれましたURLがよい資料なので、詳しくは そちらを見てください。ここでは簡単に言いますと、GCは古典的には、
- Reference Count (被参照数が0になったオブジェクトを回収)
- Mark & Sweep (生きているオブジェクトにマークをつけ、最終的にマークがつかなかったオブジェクトを回収)
- Copying (生きているオブジェクトを別の領域に詰めながらコピーして、元の領域をまとめて回収)
の3種類がありまして、他の多くのバリエーションもこれらの何らかの発展形 になってます。このうち、1.と2.はcompactionしません。Re:GCの必要性 (スコア:1)
確認ですが、
というのは、異なるサイズのオブジェクトを生成、回収した場合ですか? というのは、同じサイズばっかりだったらそもそも空きメモリの断片化は問題にならないはずなので。
ちなみに、アドレス空間を長持ちさせると(Unixのkernelはその典型)、オブジェクトの生成にともなう再初期化が大きなオーバヘッドになってきます。これは、オブジェクトが不要になった時、その中身はオブジェクトが初めて生成された時とほぼ同じになっていることが多いためです(eg 連結リストの要素の場合、前後へのポインタは初期化時も解放時もnull)。
これを解決する方法として、解放されたばかりのオブジェクトを直ちに再利用に回すことが挙げられます。Solarisのslab allocatorはこの方法を用い、オブジェクトの割り当てと初期化時間を最大で8割減らすことができています。Javaでもこういうことはやってるんでしょうか?
Re:GCの必要性 (スコア:1)
> 行われてるのではないでしょうか? compaction されるというこ
> とは、その時点でフラグメンテーションも解消される、ということ
> ですよね?違う?
> Java の Heap に関しては、激しくオブジェクトの生成/回収を
> 繰り返してもフラグメンテーションによって新規オブジェクトが
> 生成できない、とゆー事態には陥ったことがないため漠然とそう
> 思ってたんですけど…。
私も空きメモリの合計が 要求メモリサイズを上回っているうちから
out of memory を出すへたれな JavaVM は見たことのないです。
ただ、GC が行われた後はフラグメンテーションが解決されているか
と言うと必ずしもそうではないと思います。
例えば、普段の GC はフラグメンテーションの解決を行わないけど、
断片化されない最大の空き領域のサイズが要求サイズを満たさない
場合にはしょうがないので、フラグメンテーションを解決する GC
を改めて起こすという方法があります。
特に他の Java スレッドを止めずに GC スレッドがメモリを回収
して回る On-the-flay 型 GC は、生きているオブジェクトの位置
をむやみに動かせませんし、、、
コンタミは発見の母
Re:GCの必要性 (スコア:1)
実際に compaction を行わない GC 実装が存在することはもちろ
ん知っていますし、JavaVM Spec. が Heap 管理については 100%
実装者の裁量に任せている、ことも分かっていますが、しかし、
ご存じの通り Java にはポインタがありませんから、C でのよう
にプログラム側でフラグメンテーションに対処することが非常に難しく、
となると、まっとうな実装者ならばフラグメンテーションが起こら
ないように GC を設計するのではないか、という予想のもと、こと
現代的な実装の JavaVM に関していうなら、G7 さんの書込みでい
うところの「それとも、その副作用のあるGCしか使う予定が無い、
言い換えれば使おうとしている処理系のGCがお望みのアルゴリズム
であることが既に判っている、という状況」といえるのではないか、
前の書込みに補足すれば「GC がどのようなアルゴリズムで行われ
るにせよ、JavaVM においては常に compaction は行われている
と考えていいのではないでしょうか?」というのが趣旨です。
#組み込み系まで含めると必ずしも真ではないかもしれませんが、
#J2SE 以上の各社の実装を見ているとそう言えるのではないかと。
J2SE 以上の実装では半ば常識的なことながら、JavaVM Spec. で
はっきり規定された仕様ではない、という点を、G7 さんは暗に指
摘されていたのかな…?
Only Jav^Hpanese available :-)
Re:GCの必要性 (スコア:1)
>にプログラム側でフラグメンテーションに対処することが非常に難しく、
ああ。メモリプールというかmallocに相当するものを自作するという話題ですか。
たしかにjavaでは何処をどういじってもソレっぽいことは出来ないですね。
>現代的な実装の JavaVM に関していうなら、G7 さんの書込みでい
>うところの「それとも、その副作用のあるGCしか使う予定が無い、
>言い換えれば使おうとしている処理系のGCがお望みのアルゴリズム
>であることが既に判っている、という状況」といえるのではないか、
それを称して「現代的」と呼ぶんでしょうか?>識者諸兄
俺は知らないんですが。
>JavaVM においては常に compaction は行われている
そこでいう「JavaVM」がどこまでを指すか?に拠るでしょうね。
Sunなりなんなりの1つ(^^;の実装について語りたいなら、
メーカーに質問するとか、気に入らないなら(金を出して)変更を迫るとか、
いろんな手が有り得そうです。
でも、KaffeやWavaみたいな偽Java(^^;とか、あるいは各種(?)小型組み込み向けJavaとか、も
含めて考えると、その期待が満たされてるかどうかは、また違う話になるわけですよね。
>#J2SE 以上の各社の実装を見ているとそう言えるのではないかと。
上に書きましたが、Kaffeって、どう捉えたらいいんでしょうね?(^^;
J2SEとは…あ、どうせ言えないのか。
Java1.2相当にも、まだなってないんでしたっけかあれ?
… http://www.kaffe.org/ … あ。まだ1.1相当かあ。
あんまり厳密に考える必要はないけど... (スコア:1)
意味で使っていると思うのですが、
厳密に言うと GC の世界では compaction は in place(同じ領域内で)にオブジェクトをつめる処理を指すので、
3. の Copying GC も compaction はやらないと思います。
コンタミは発見の母
Re:GCの必要性 (スコア:1)
それ、もしかして、解放された領域を、「同じ種類」ごとに
別々のフリーリストにぶら下げたりする、んでしょうか?
だとしたら、種類という概念がクラスのおかげ(乱暴な言いかただが)で
C的世界よりずっとはっきりしているoop処理系においては、
より旨くやれるんではないでしょうか?
つまり卑近に言えば、多くてもせいぜいClassの数と同じ数のフリーリストを作ればいい、
リストをDictionaryにぶらさげて、リストをDictの中で選択するためのキーはjava.lang.Classである、
みたいな感じで…?(^^;
#そういう意味では、所詮(ごめん)C世界でしかないunix系カーネルとは
#いっしょにならんというか、もっともっとエレガントにやれるというか、ではないかなあ。
Re:GCの必要性 (スコア:1)
厳密には、page level allocator(つまりvirtual memory)から切り出してきた、free objectのcacheに放り込みます。このcacheはper object typeです。
それはなんともいえません。Uresh Vahaliaは著書Unix Internals: The New Frontiers [amazon.com]の中で、以下のようなslab allocatorの欠点を指摘しています(以下は邦訳より)。
となると、cacheを使うか否かを決める問題が生じます。Solarisの場合、私が本や実装を(誰か1994年夏のUsenix [usenix.org]予稿集持ってませんか?)見た限りでは、cacheを使うか否かはobject type毎にhardcodeされている(すなわち人間が決めている)ようです。Unix kernelならこれでも何とかなりますが、個々のプログラムを支える枠組み、すなわち言語処理系やruntime libraryなどの場合は機械的に決めないと使いものにならないでしょう。Solarisがこれをやっていないということは、機械的な決定は難しいということでしょうか。
フリーリストは使わんです (スコア:1)
空き領域の管理をフリーリストではなく、下から順番に詰めて
使って行くヒープポインタ(というのか?)で管理していると思われます。
ヒープポインタを確保したサイズ分増やすだけなので総合的に見てスピードが速いのです。
少なくも SUN JDK1.3、1.4 はこの方式です。
ClassiVM はインスタンスを指すハンドラとハンドラの実体
に分かれていて、ハンドラ領域はフリーリスト管理で、実体を
格納するヒープ領域はヒープポインタ管理です。
# ハンドラは全部同じ大きさ。
コンタミは発見の母
現代的な GC (スコア:1)
> 俺は知らないんですが。
compaction をやることが現代的な GC だとは思いません。
長い GC の歴史の中である程度 よい GC の条件が見えてきています。
非並列 GC の場合に限ると以下の 4点ぐらいを押さえた GC が現代的
な GC ではないでしょうか?
1. オブジェクトの寿命を意識すること
オブジェクトには生成されたけど一度も使われずに終わる
単寿命なやつから VM が終わるまで居続ける長生きなオブ
ジェクトまで寿命に差があります。
現代の GC はこの性質を旨く使う事が何より求められています。
2. キャッシュを意識すること
現代的なプロセッサはキャッシュの性能におんぶでだっこ。
GC といえどもキャッシュミスヒットを避ける努力が必要です。
3. 排他制御は最小に
fetch & add や compare & swap のようなアトミック命令は
最初にするのが吉です。
OS の同期オブジェクトの極力使わないことが求められます。
4. 処理は短く
それぞれの操作(例えば 1回の new)にかかる時間を減らすことも
重要です。
それ以外にも stop the world を掛けてから本当にすべてのスレッド
が止まって GC がはじまるまでのタイムラグだとかがあります。
コンタミは発見の母
Re:GCの必要性 (スコア:1, 参考になる)
> GCを利点として挙げる人がいますが、それも僕はどうかと思っています。
> GCがあるためにむちゃくちゃなプログラムでもある程度動いてしまいます。
これは、null なのに使おうとしたって事で、C++とJavaに差は余り無い気がします。
GCとは関係ないのでは?
> 1時間ぐらいだったら動くけど長時間動かしているとVMが落ちることがありますし、その時のバグを見つけるのが非常に大変です。
これは、メモリリークしているということだとすると、GCのおかげで、それは無くなるんではないでしょうか?
メモリが無くなっているとしても、直接には、別の原因でVMが落ちているのでは無いでしょうか?
GCのおかげで、deleteを書かなくて良いとか、ポインタ変数を、参照出来なくなっても良いとか言うのはかなり良いと思います。
それと、APIまでJava言語に含まれているおかげで、スレッドも大抵のJavaの本で触れられているし、C++に比べ簡単になること自体で本の内容がそれを埋める分だけ色々増えているのは良いです。
Re:GCの必要性 (スコア:1)
関係はあると思います。
ガベージコレクタがオブジェクトの回収をやってくれるおかげで、メモリリークが顕在化しにくくなったため、オブジェクトの管理がいい加減なプログラムでも、それなりに動いてしまう、という話では?
で、その結果、真綿で首を絞めるように、回収されない(できない)オブジェクトがじわじわと蓄積して、
となると。
「Java(の)メモリリーク」などと呼ばれるようです。
# 私自身は「だからGCに利点はそれほどない」とは思いませんが。
Re:Javaの必要性 (スコア:1)
>Write Once Run Anywareとか言っていますがはっきり言って実現されて無いと思います。
それはおっしゃる通りです。おれもなんだかんだ言って結局は、
Windowsクライアントでソース書く->Unixのサーバー上にftpしてコンパイル
なんてしたましたし(笑)今はサーバーもクライアントもlinuxだからその点楽。
>移植性 + 速度
>で考えるとCの方が上だと思っています。
write once....は「コンパイル済みのバイナリコードがそのまま移植できる」ということだと思うのだけど。Cの移植性(ソースもってってコンパイルすればOK)とは別の話になると思いますが。
ソースの移植性についても、#ifdef WIN32みたいなマネをする箇所がjavaならかなり減るのでは?、特にGUIについては。
というか、javaにマクロは無いが<-おれにとってはこれがjavaの嫌なとこです(笑)
それに、たとえば顧客にUNIX上で動くPGを納品するときに、ソースに#ifdef WIN32とか書いてあったらマズイ(笑)
速度に関しては、たしかに遅いですね。GUIのアプリをまともに作る気分にはなれない。
>最後にIDEです。
>デバッグが難しいのにろくなIDEが無いために開発が非常に面倒です。
xemacs + javac + jdbで開発してます(笑)
#そいえばCもdbxでやってたな