- PR -

ちょっと突っ込んだ質問ですが

投稿者投稿内容
TO-R
ベテラン
会議室デビュー日: 2002/07/11
投稿数: 93
投稿日時: 2002-12-17 14:30
>issekiさん

引用:

ただ、コードの複製に関してはどなたも
触れませんでしたので、改めて質問させていただきたいです。

JAVAコード(JAVAの文、例えばfor(..))はnewする時に必ずどっかのメモリへ複製するのでしょうか。


逆に質問ですが、(実際にコードを複製するかどうかは、とりあえず置いておいて)
コードを複製する「メリット」や「必要性」があると思われますか?

引用:

皆さんの見解をまとめますと、以下のようでしょうね。
A.loadする時は、*.classのコード部分とstaticの部分(static method とstatic variable)をメモリへ展開(確保)する


staticなメソッドのハンドルは、「クラスそのもの」に属するので、ロード
と同時に呼べる状態になります。

staticでないメソッドは、インスタンスに属するので、インスタンスが生成
されて始めて呼び出し可能になります。

その時、コードはどうなるか考えてみると…
複製されるとしたら、個々のインスタンスの一部として領域を確保され、
個々のインスタンスは自分のコードを処理することになるでしょうか?
一方、複製されないとしたら、個々のインスタンスは、変数のみ確保して、
コードは、ロードされたクラスのものを使用することになるでしょうね。

(x86風に表現すると…)コード・セグメントと、データ・セグメントは別々に
定義するでしょうから、コードを共有しても不具合は無いですし、
逆に複製すると、同じものを入れるメモリを確保したり、さらに複製する手間が
無駄ですよね?

  それでも、何らかの理由で複製しているかもしれませんが…:-P


ここはひとつ、プログラムを作って試して見られては?
巨大なダミーの非staticのメソッドを持ったクラスを作って、インスタン
スを生成して、メモリの使用量を調べられたらわかるのでは?

  結果はぜひここでも報告してください!!

[ メッセージ編集済み 編集者: TO-R 編集日時 2002-12-17 14:33 ]
isseki
大ベテラン
会議室デビュー日: 2001/11/05
投稿数: 107
投稿日時: 2002-12-17 15:18
TO-R
こんにちは
ご返答ありがとうございます。

>巨大なダミーの非staticのメソッドを持ったクラスを作って、インスタン
スを生成して、メモリの使用量を調べられたらわかるのでは?

この巨大さに怖がって、すぐに応じられませんが、

非staticのメソッドが複製されるのではないかと疑った理由として
ロードした直後に実行できるmain()関数の中に
同じclassの非staticのメソッドをcallするのを許せないとは
非staticのメソッドがメモリに存在しているにも関わらず、
有効なコード領域として見なされないのではないかと思ったのです。




isseki
大ベテラン
会議室デビュー日: 2001/11/05
投稿数: 107
投稿日時: 2002-12-17 15:19
大変失礼致しました!

誤:TO-R
正:TO-R さん
お詫びいたします。

TO-R
ベテラン
会議室デビュー日: 2002/07/11
投稿数: 93
投稿日時: 2002-12-17 17:36
>issekiさん

引用:

非staticのメソッドが複製されるのではないかと疑った理由として
ロードした直後に実行できるmain()関数の中に
同じclassの非staticのメソッドをcallするのを許せないとは
非staticのメソッドがメモリに存在しているにも関わらず、
有効なコード領域として見なされないのではないかと思ったのです。


main()メソッド(←当然static)が実行できるのは、先のカキコの
「staticなメソッドはclassの付属品」という解釈で、ロードされたら
有効ということOKですよね?
そこからstaticなメソッドが呼べるのも、既にロードされて有効だからです。
今回問題の、「非staticなメソッドは、ロード済みなのに呼べない」のは、
先のカキコのとおり、「非staticなメソッドはインスタンスの付属品」という
解釈なので、インスタンスを生成しないと呼べない」というルールです。

よって、このことが、コードが複製される(あるいは、複製されない)根拠には
ならないと思います。 でも、疑問を持つのは良いことだと思います。小学生の
頃に見た理科や算数の番組の「うん、いいところに気がついたね」ですね(^^)


  “巨大なコード”は少々大袈裟だったでしょうか…(^^;
  実数の演算(コンパイル時に最適化されないような式)と表示を
  ベタに100ぐらい書けば、目に見えるぐらいの領域になるで
  しょうか…。
  
---

引用:

大変失礼致しました!


いえいえ、お気になさらず(^^)

  ちなみに、発言の直下の[編集]をクリックすると、修正や削除ができます。
  15:18分を編集して、15:19は削除しておかれてはいかがでしょうか?


[ メッセージ編集済み 編集者: TO-R 編集日時 2002-12-17 17:39 ]
H2
ぬし
会議室デビュー日: 2001/09/06
投稿数: 586
お住まい・勤務地: 港
投稿日時: 2002-12-17 18:49
引用:

issekiさんの書き込み (2002-12-17 13:07) より:
ただ、コードの複製に関してはどなたも
触れませんでしたので、改めて質問させていただきたいです。

JAVAコード(JAVAの文、例えばfor(..))はnewする時に必ずどっかのメモリへ複製するの
でしょうか。

よろしくお願いいたします。



> クラスのロード時には最低でもstatic変数、staticメソッドとインスタンスメソッド
> がメモリにロードされる必要がありますが、オブジェクトの生成にはインスタンス変
> 数のみのメモリが必要です。参照やパディングがあるのでもうちょっと必要ですが・・・。
と書きましたよ。

TO-Rさんが言われるように、オブジェクトの生成毎にわざわざコード部分を複製するメリットは思いつきません。一般的にメモリ(正確にはVirtualメモリ)内ではデータセグメントとコードセグメントを分断するのが普通です。わざわざコード部分をコピーしていたらどこからどこまでがコードセグメントで、どこがデータセグメントなのか分からなくなってしまいます。さらに、コード部分は普通Read-onlyなのでコードの実行中に変わることはまずありえません。つまりメモリの複製をするのは領域の無駄です。もう一つおまけに、オブジェクトの生成は結構頻繁に起こるので、オーバーヘッドを減らすためにはメモリ読み書き込みは減らす必要があります。

とはいうものの、実際はどうなんでしょう?私も実験結果が知りたいです。
へげもん
ベテラン
会議室デビュー日: 2002/04/14
投稿数: 87
お住まい・勤務地: 埼玉県
投稿日時: 2002-12-17 20:24
インスタンスを生成しないとstaticでないメソッドが呼べない理由は、それらのメソッド全てが隠れた第一引数としてthisを受け取る必要があるからです。
仮に、インスタンスを生成せずに非staticメソッドが呼べてしまうとすると、this==nullとなってしまい、ほとんどの場合、null pointer exceptionが連発されてしまいます。

以上、「非staticなメソッドはインスタンスの付属品」をメソッドの側から説明してみました。
t-wata
大ベテラン
会議室デビュー日: 2002/07/12
投稿数: 209
お住まい・勤務地: 東京
投稿日時: 2002-12-17 20:37
> とはいうものの、実際はどうなんでしょう?私も実験結果が知りたいです。

java.lang.Stringのようにインスタンスメソッドをいっぱい持ってるクラスの
インスタンスを大量に生成して、メモリ使用状況を調べればいいでしょう。

そんなことする必要も無いでしょうが。
Kissinger
ぬし
会議室デビュー日: 2002/04/30
投稿数: 428
お住まい・勤務地: 愛知県
投稿日時: 2002-12-18 00:04
実験するまでもありません。
インスタンス生成でコードはコピーされません。(仕様で禁止してないので、そういうVM作れないことはないでしょうが。)
実験する誘惑にかられたら JVMのソースを読んだほうが良いと思われます。(特定の実装ということにはなりますが。)

H2さんの回答がズバリです。
(ただし、クラスをロードした場合には1〜3の他に『バイトコードの検証』も行われる点も忘れないどいたほうが何かと役に立ちます。)

スキルアップ/キャリアアップ(JOB@IT)