简体   繁体   中英

Why InlineShape.add in Word2013 leads to memory leak

My program must add photos to the Word Document table. Faced with the fact that in Word 2013 the program works much slower or even hangs up. I began to look for problem areas and it seems that the problem is in the memory occupied when adding images.

I add images to Word 2013 table by InlinesShapes.AddPicture method. after that, the used memory increases by ~ 50 Mb for each image. When it reaches ~600 mb it stops growing at this rate and the growth is about 1 mb. Then at some point Word clears memory up to 200 and all over again.

But if i do the same in Word 2007 the amount of siezed memory less than 1 kb, alltime.

Word 2007 on my Notebook (Win 8.1, i5-4300u), Word 2013 install on other machine (Virtual Desktop with Win 7, Xeon E5) - if it matter.

I'm adding the usual photos taken with the camera, for example: 4160x3120, 72 dpi, 24 bit, 500 Kb size, JPG.

That sample code with used memory calculation

Sub A()  
    ' >-- SOME CODE --<

    Dim objCell As Word.Cell
    'user method that return first free Word.Cell from table
    Set objCell = TableManager.Get_FreeCell(objTable) 
    'clear
    Tools.MemCheck "<- mem before paste"

    objCell.Range.InlineShapes.AddPicture sFilePath 

    'clear
    Tools.MemCheck "-> mem after paste"

    ' >-- SOME CODE --<

    Set objCell = Nothing
 End Sub

Output by Word2013

    296.156 Mb <- mem before paste
    345.793 Mb -> mem after Paste
    346.504 Mb <- mem before paste
    396.18  Mb -> mem after Paste

Output by Word2007

    109.867 Mb <- mem before paste
    109.871 Mb -> mem after Paste
    109.871 Mb <- mem before paste
    109.879 Mb -> mem after Paste
    109.887 Mb <- mem before paste
    109.887 Mb -> mem after Paste

There is code of MemCheck. Declared mobjSWbemServices as global, to exclude it from the problem.

Dim mobjSWbemServices as Object
Sub MemCheck(Optional ByVal sDescription As String = vbNullString)
    If mobjSWbemServices is nothing then Set mobjSWbemServices = GetObject("winmgmts:")
    Dim GetMemUsage As Double
     GetMemUsage = mobjSWbemServices.Get( _
        "Win32_Process.Handle='" & _
        GetCurrentProcessId & "'").WorkingSetSize / 1024 / 1024    

    Debug.Print Round(GetMemUsage, 3); " Mb"; vbTab; sDescription
   'GetCurrentProcessId  is Declared Library: 
     'Private Declare PtrSafe Function GetCurrentProcessId Lib "kernel32" () As Long
     'Private Declare Function GetCurrentProcessId Lib "kernel32" () As Long
End Sub

So what could be the problem? Am I doing something wrong or is it a bug and I need to install some updates?

There was a major change in the graphics engine used between Word 2007 (and 2010) and Word 2013 (and later versions). That could be a factor. It's also a fact that the object model is slower in Word 2013 (and later), partly for security reasons, as I recall. So there may not be a lot you can do.

One thing you can try is to clear Word's UNDO stack and explicitly SAVE the document. This will reduce the number of objects Word is managing in order to support Undo and could speed things up.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM