| 
          
            □投稿者/ 魔界の仮面弁士 (930回)-(2008/12/03(Wed) 12:56:25)
              | ■29016 / inTopicNo.4) | Re[3]: Excelのメモリ開放について(遅延バインディング方式) |  
 
          
            
              
                |  | 2008/12/03(Wed) 14:40:05 編集(投稿者) 
 ■No29014 (blueblur さん) に返信
 > ただしVB6時代から多用された遅延バインディング方式では、
 むしろ、型変換にともなって参照カウントが増加するなどの理由から、
 レイトバインドの方が、解放が難しくなる事さえありえます。
 
 例えば、
 Dim Hs As Excel.HPageBreaks = objSheet1.HPageBreaks
 Dim H As Excel.HPageBreak = Hs.Add(objRange)
 Marshal.ReleaseComObject(H)
 Marshal.ReleaseComObject(Hs)
 Marshal.ReleaseComObject(objRange)
 Marshal.ReleaseComObject(objSheet1)
 ならば正しく解放されたコードが、参照設定無しだと
 Dim Hs As Object = objSheet1.HPageBreaks
 Dim H As Object = Hs.Add(objRange) 'ここで参照カウントが増加してしまう。
 Marshal.ReleaseComObject(H)
 Marshal.ReleaseComObject(Hs)
 Marshal.ReleaseComObject(objRange) 'そのため、ここで解放してもまだ一つ残っている…。
 Marshal.ReleaseComObject(objSheet1)
 という結果になってしまった事がありました。
 http://hpcgi1.nifty.com/MADIA/VBBBS2/wwwlng.cgi?print+200512/05120042.txt
 
 
 > (VB.NETでも)InteropなしでNothingを与えるだけで開放できたようです。
 だとしたら、それはただの偶然かも知れません。
 (.NET 側のメモリ管理と COM のメモリ管理は別物です)
 
 実際当方では、Nothing 代入による
 Sub Main()
 Dim o As Object = CreateObject("Excel.Application")
 o.Quit()
 MsgBox("これから解放します。", vbSystemModal)
 o = Nothing
 MsgBox("解放されていますか?", vbSystemModal)
 End Sub
 というコードにおいて、タスクマネージャ上に「EXECEL.EXE」のプロセスが残ってしまう事を
 確認しています。(アプリが終了すれば、続けて解放される可能性がありますけれども)
 
 
 一方、ReleaseComObject を呼び出した場合においては、アプリを終了させずとも、
 ReleaseComObject の呼び出しによって、タスクマネージャ上から「EXECEL.EXE」が
 即座に消える事を確認しています。
 
 Sub Main()
 Dim o As Object = CreateObject("Excel.Application")
 o.Quit()
 MsgBox("これから解放します。", vbSystemModal)
 System.Runtime.InteropServices.Marshal.ReleaseComObject(o)
 MsgBox("解放されていますか?", vbSystemModal)
 End Sub
 
 |  |