今日は、日本HPの近藤です。
いつも質問ばかりで恐縮ですが、どなたか教えてください。 Smalltalkでプログラミングしていると自分の作ったインスタンスが システムにどんどん増えて、プログラムを更新して新しいインスタンスが できたのに古いインスタンスが、どこかでゾンビのように生き残っていて 新しい更新した機能が出てこないような気がすることがあります。 いまシステムにいるインスタンスを表示して古いゾンビのインスタンス を殺したいのですが、こんなことできますでしょうか? 近藤 |
おだです。
> いまシステムにいるインスタンスを表示して古いゾンビのインスタンス > を殺したいのですが、こんなことできますでしょうか? 殺せるかどうかは別として、あるクラスのインスタンスを得るには クラス名 allInstances をインスペクトすればいいです。 --- おだ |
おださん、
早速のご教示、誠にありがとうございます。 家に帰ったら早速試してみます。 近藤 -----Original Message----- From: [hidden email] [mailto:[hidden email]] On Behalf Of Tomohiro Oda Sent: Monday, June 02, 2008 11:44 AM To: Squeak discussion in Japanese Subject: [Squeak-ja: 3901] Re: ゾンビインスタンス おだです。 > いまシステムにいるインスタンスを表示して古いゾンビのインスタンス > を殺したいのですが、こんなことできますでしょうか? 殺せるかどうかは別として、あるクラスのインスタンスを得るには クラス名 allInstances をインスペクトすればいいです。 --- おだ |
ついでにもうひとつ教えてください。
クラス名 allInstances 上記をインスペクトしたらArrayというのが出て、all inst varsの中に43個ほど 番号つきでクラス名(番号)というものが出てきたのですが、これ全部インスタンスで システムの中にいるってコトですか? デバッグすればするほどインスタンスの残骸がシステムに残るのでしょうか? 掃除しなくても大丈夫なのでしょうか? 近藤 -----Original Message----- From: [hidden email] [mailto:[hidden email]] On Behalf Of Kondo, Fumito Sent: Monday, June 02, 2008 1:03 PM To: Squeak discussion in Japanese Subject: [Squeak-ja: 3902] Re: ゾンビインスタンス おださん、 早速のご教示、誠にありがとうございます。 家に帰ったら早速試してみます。 近藤 -----Original Message----- From: [hidden email] [mailto:[hidden email]] On Behalf Of Tomohiro Oda Sent: Monday, June 02, 2008 11:44 AM To: Squeak discussion in Japanese Subject: [Squeak-ja: 3901] Re: ゾンビインスタンス おだです。 > いまシステムにいるインスタンスを表示して古いゾンビのインスタンス > を殺したいのですが、こんなことできますでしょうか? 殺せるかどうかは別として、あるクラスのインスタンスを得るには クラス名 allInstances をインスペクトすればいいです。 --- おだ |
こんにちは、阿部です。
08/06/02 に Kondo, Fumito<[hidden email]> さんは書きました: > クラス名 allInstances > > 上記をインスペクトしたらArrayというのが出て、all inst varsの中に43個ほど > 番号つきでクラス名(番号)というものが出てきたのですが、これ全部インスタンスで > システムの中にいるってコトですか? はい、そうです。 > デバッグすればするほどインスタンスの残骸がシステムに残るのでしょうか? > 掃除しなくても大丈夫なのでしょうか? Smalltalkには自動メモリ管理機能があるので、明示的にオブジェクトのメモリを確保したり、開放したりしなくてもよいという話は良く聞きます。これは事実そのとおりで、とても便利です。ただ、気をつけないといけないのは、Smalltalkがどのようにオブジェクトを管理しているかということです。 たぶんここで問題にしているのはモーフのことだと思うので、例となるモーフのクラスを作ります。 このメールの内容をワークスペースにコピー&ペーストして、以下の式をdo it(式を評価)してください。 Morph subclass: #TestMorph instanceVariableNames: '' classVariableNames: '' poolDictionaries: '' category: 'Morphic-Test' まず、このクラスのインスタンスがないことを確認します。以下をprint it(式を表示)で評価します。 TestMorph allInstances size 結果はもちろん0です。 続いて、インスタンスを作ります。このとき、必要なメモリが自動的に確保されます。 TestMorph new. これでインスタンスができました。では、再度インスタンスの数を調べましょう。 TestMorph allInstances size. 1を期待したのに0が返りませんでしたか。それは、すでにインスタンスが消滅しているからです。Smalltalkは、このように他から参照されていないオブジェクトのメモリを自動的に開放してくれます。では、次はどうでしょうか。 TestMorph new openInWorld. TestMorph allInstances size. 今度は1が返ったと思います。TestMorphのインスタンスを画面に開いたとき、ActiveWorldやその他のオブジェクトから参照されたからです。では、これを画面から消して見ましょう。 TestMorph allInstances first delete. TestMorph allInstances size. 再び0に戻りました。これは何個でも同じことです。 10 timesRepeat: [TestMorph new openInWorld]. TestMorph allInstances size. TestMorph allInstances do: [:each | each delete]. TestMorph allInstances size. ここでいう参照とは、どこかのオブジェクトの変数にインスタンスが束縛されていることです。次の式をprint itしてください。 foo := TestMorph new. TestMorph allInstances size. この例では、fooはワークスペース変数なので、ワークスペースを閉じるか、明示的に変数を他で初期化するまで参照は切れません(インスタンスは消えません)。他の変数の場合もその寿命によります。 foo := nil. TestMorph allInstances size. さきほど使ったdeleteは、その中でこのような変数の初期化を行っています。 また、インスペクタやデバッガなどのツールも、対象のオブジェクトを参照するので、それらを閉じるまで参照は切れません。 TestMorph new inspect. TestMorph allInstances size. 1が返ると思います。では、インスペクタを閉じてから再び上の式をprint itすると0が返るかと思いきや、タイミングによっては1が返る場合があります。しばらく待てば、ガーベジコレクタが動いてゴミ収集されるのですが、これを明示的に行う場合は以下の式を評価します。 Smalltalk garbageCollect. これで0に戻るはずです。 以上のように、適切に扱えばSmalltalkに不要なオブジェクトが残ることはありません。よくあるのは、要らなくなったツールを開きっぱなしだったり、グローバル変数やクラス変数などの寿命の長い変数に束縛したのを忘れたり、自分で作成した部分について、不要になったときに参照を切る処理をしていなかったりなどです。このような状況のままイメージを保存すると、それらも含めて永続化されます。 時間が経って、どのような状況か分からなくなった後に何百個、何千個とあるものを一個一個確認して消していくのは困難を極めます(遠い昔に恐ろしいものを見たことがあります)。 早めの対処をお勧めします。 //abee -- 阿部 和広 EMAIL [hidden email] |
増田@電大です。
話は直接関係ありませんが、昔、Smalltalk-80 を使っていたころ、自分で作っ たクラスのインスタンスが大量に残っているのにそのクラスを消したことがあ り、イメージ中に Obsolete というオブジェクトがたくさんできたことがあ ります。(^.^;;) 今、VisualWorks で Hoge というクラスを作って、H := Hoge new. して H をインスペクトした後に、クラス Hoge を消してみたら、インスペクタの表 示が AnObsoleteHoge になりました。self class allInstances したら、 インスタンスの一覧は捕まえられました。Smalltalk inspect してみても AnObsoleteHoge がみつからないのですが、どこにあるんでしょうね。 それから、VisualWorks の時には、コントローラに close メッセージを送ら ないといけないのに、ビューに close を送ってしまうコードを書いていた人 がいて、ScheduledControllers にコントローラだけ残りまくってたことがあ りましたね。ビューがないコントローラに release メッセージを投げまくり ました。 > From: "Kazuhiro ABE" <[hidden email]> > > 時間が経って、どのような状況か分からなくなった後に何百個、何千個とあ > るものを一個一個確認して消していくのは困難を極めます(遠い昔に恐ろし > いものを見たことがあります)。 ------ 〒101-8457 東京電機大学 未来科学部 情報メディア学科 増田 英孝 E-mail: [hidden email] TEL 03-5280-3551 http://www.cdl.im.dendai.ac.jp/%7Emasuda/ FAX 03-5280-3592 It's more fun to compute! |
In reply to this post by Kazuhiro ABE-3
阿部さん、
丁寧な解説をどうもありがとうございます。 理解がぐっと深まりました。 今後ともよろしくお願いいたします。 近藤 -----Original Message----- From: [hidden email] [mailto:[hidden email]] On Behalf Of Kazuhiro ABE Sent: Monday, June 02, 2008 3:51 PM To: Squeak discussion in Japanese Subject: [Squeak-ja: 3906] Re: ゾンビインスタンス こんにちは、阿部です。 08/06/02 に Kondo, Fumito<[hidden email]> さんは書きました: > クラス名 allInstances > > 上記をインスペクトしたらArrayというのが出て、all inst varsの中に43個ほど > 番号つきでクラス名(番号)というものが出てきたのですが、これ全部インスタンスで > システムの中にいるってコトですか? はい、そうです。 > デバッグすればするほどインスタンスの残骸がシステムに残るのでしょうか? > 掃除しなくても大丈夫なのでしょうか? Smalltalkには自動メモリ管理機能があるので、明示的にオブジェクトのメモリを確保したり、開放したりしなくてもよいという話は良く聞きます。これは事実そのとおりで、とても便利です。ただ、気をつけないといけないのは、Smalltalkがどのようにオブジェクトを管理しているかということです。 たぶんここで問題にしているのはモーフのことだと思うので、例となるモーフのクラスを作ります。 このメールの内容をワークスペースにコピー&ペーストして、以下の式をdo it(式を評価)してください。 Morph subclass: #TestMorph instanceVariableNames: '' classVariableNames: '' poolDictionaries: '' category: 'Morphic-Test' まず、このクラスのインスタンスがないことを確認します。以下をprint it(式を表示)で評価します。 TestMorph allInstances size 結果はもちろん0です。 続いて、インスタンスを作ります。このとき、必要なメモリが自動的に確保されます。 TestMorph new. これでインスタンスができました。では、再度インスタンスの数を調べましょう。 TestMorph allInstances size. 1を期待したのに0が返りませんでしたか。それは、すでにインスタンスが消滅しているからです。Smalltalkは、このように他から参照されていないオブジェクトのメモリを自動的に開放してくれます。では、次はどうでしょうか。 TestMorph new openInWorld. TestMorph allInstances size. 今度は1が返ったと思います。TestMorphのインスタンスを画面に開いたとき、ActiveWorldやその他のオブジェクトから参照されたからです。では、これを画面から消して見ましょう。 TestMorph allInstances first delete. TestMorph allInstances size. 再び0に戻りました。これは何個でも同じことです。 10 timesRepeat: [TestMorph new openInWorld]. TestMorph allInstances size. TestMorph allInstances do: [:each | each delete]. TestMorph allInstances size. ここでいう参照とは、どこかのオブジェクトの変数にインスタンスが束縛されていることです。次の式をprint itしてください。 foo := TestMorph new. TestMorph allInstances size. この例では、fooはワークスペース変数なので、ワークスペースを閉じるか、明示的に変数を他で初期化するまで参照は切れません(インスタンスは消えません)。他の変数の場合もその寿命によります。 foo := nil. TestMorph allInstances size. さきほど使ったdeleteは、その中でこのような変数の初期化を行っています。 また、インスペクタやデバッガなどのツールも、対象のオブジェクトを参照するので、それらを閉じるまで参照は切れません。 TestMorph new inspect. TestMorph allInstances size. 1が返ると思います。では、インスペクタを閉じてから再び上の式をprint itすると0が返るかと思いきや、タイミングによっては1が返る場合があります。しばらく待てば、ガーベジコレクタが動いてゴミ収集されるのですが、これを明示的に行う場合は以下の式を評価します。 Smalltalk garbageCollect. これで0に戻るはずです。 以上のように、適切に扱えばSmalltalkに不要なオブジェクトが残ることはありません。よくあるのは、要らなくなったツールを開きっぱなしだったり、グローバル変数やクラス変数などの寿命の長い変数に束縛したのを忘れたり、自分で作成した部分について、不要になったときに参照を切る処理をしていなかったりなどです。このような状況のままイメージを保存すると、それらも含めて永続化されます。 時間が経って、どのような状況か分からなくなった後に何百個、何千個とあるものを一個一個確認して消していくのは困難を極めます(遠い昔に恐ろしいものを見たことがあります)。 早めの対処をお勧めします。 //abee -- 阿部 和広 EMAIL [hidden email] |
In reply to this post by Hidetaka MASUDA
おだです。
> 今、VisualWorks で Hoge というクラスを作って、H := Hoge new. して > H をインスペクトした後に、クラス Hoge を消してみたら、インスペクタの表 > 示が AnObsoleteHoge になりました。self class allInstances したら、 > インスタンスの一覧は捕まえられました。Smalltalk inspect してみても > AnObsoleteHoge がみつからないのですが、どこにあるんでしょうね。 Behaviorのクラス変数にObsoleteSubclassesというWeakKeyToCollection があって、それはキーがAnObsolete superclassに、値側にWeakArrayがあって、 そのWeakArrayの中に格納されています。 --- おだ |
おだです。言い忘れてましたが、下記はSqueakの場合です。Visual Worksのほうは
最近すっかりいじってないので忘れてしまいました :-) --- おだ Tomohiro Oda wrote: > おだです。 > >> 今、VisualWorks で Hoge というクラスを作って、H := Hoge new. して >> H をインスペクトした後に、クラス Hoge を消してみたら、インスペクタの表 >> 示が AnObsoleteHoge になりました。self class allInstances したら、 >> インスタンスの一覧は捕まえられました。Smalltalk inspect してみても >> AnObsoleteHoge がみつからないのですが、どこにあるんでしょうね。 > > Behaviorのクラス変数にObsoleteSubclassesというWeakKeyToCollection > があって、それはキーがAnObsolete superclassに、値側にWeakArrayがあって、 > そのWeakArrayの中に格納されています。 > --- > おだ > > |
Free forum by Nabble | Edit this page |