Profiling.XML.MassReplace
Download: 20111223.Profiling.XML.MassReplace as zip package
;==========================================================================================================================================
;
; Profiling Performance Contest.
;
;   - 20111216.HowTo.XML.MassReplace.1.wbt  (StrIndexWild)
;   - 20111218.HowTo.XML.MassReplace.2.wbt  (Binary Buffer)
;   - 20111219.HowTo.XML.MassReplace.3.wbt  (DOM Extender)
;   - 20111220.HowTo.XML.MassReplace.4.wbt  (Microsoft XML DOM)
;   - 20111220.HowTo.XML.MassReplace.5.wbt  (Regular Expression)
;   - 20111220.HowTo.XML.MassReplace.6.wbt  (FileRead)
;   - 20111223.HowTo.XML.MassReplace.7.wbt  (Microsoft XML DOM XSLT)
;
;------------------------------------------------------------------------------------------------------------------------------------------
; (c)Detlev Dalitz.20111223.
;==========================================================================================================================================

DirChange (DirScript ())

; How many different test cases?
intContestCaseMax = 2

; How many loops to run?
intContestLoopMax = 1

; What group of contestants to examine?
intContestantMin = 1
intContestantMax = 7

; Display preview of test case results?
;blnDisplayPreview = @TRUE
blnDisplayPreview = @FALSE

; Display contest status in windows title?
blnDisplayStatus = @TRUE
;blnDisplayStatus = @FALSE

GoSub DEFINE_CONTEST_FUNCTIONS


;==========================================================================================================================================
GoSub DEFINE_FUNCTIONS

; Run the contest once and display the results for verifying.
; Then press CANCEL to abort or OK to run complete contest.
If blnDisplayPreview
   For intContestCase = 1 To intContestCaseMax
      udsPrepareTestCase (intContestCase)
      udsPrepareCounters ()
      For intContestant = intContestantMin To intContestantMax
         udsRunContestant (intContestant)
      Next
      If @CANCEL == udfArrayDumpToItemList (arrContestResults, intContestantMin, intContestantMax, @LF) Then Goto CANCEL
   Next
EndIf

; Run complete contest.
WinShow ("")
strContestResult = ""

Switch blnDisplayStatus
Case @TRUE
   For intContestCase = 1 To intContestCaseMax
      udsPrepareTestCase (intContestCase)
      udsPrepareCounters ()
      For intContestLoop = 1 To intContestLoopMax
         For intContestant = intContestantMin To intContestantMax
            WinTitle ("", "Profiling|Case=" : intContestCaseMax : "." : intContestCase : "|Contestant=" : intContestantMax : "." : intContestant : "|Loop=" : intContestLoopMax : "." : intContestLoop)
            udsRunContestant (intContestant)
         Next
      Next
      strContestResult = strContestResult : @LF : udsResultPerTestCase ()
   Next
   Break
Case @FALSE
   For intContestCase = 1 To intContestCaseMax
      udsPrepareTestCase (intContestCase)
      udsPrepareCounters ()
      For intContestLoop = 1 To intContestLoopMax
         For intContestant = intContestantMin To intContestantMax
            udsRunContestant (intContestant)
         Next
      Next
      strContestResult = strContestResult : @LF : udsResultPerTestCase ()
   Next
   Break
EndSwitch

strContestResult = strContestResult : @LF : strPre : StrFill ("-", intLenSum)
strContestResult = StrSub (strContestResult, 2, -1)

Message (strMsgTitle, strContestResult)
ClipPut (StrReplace (strContestResult, @LF, @CRLF))

:CANCEL
Exit
;==========================================================================================================================================



;==========================================================================================================================================
:DEFINE_CONTEST_FUNCTIONS
;==========================================================================================================================================

;------------------------------------------------------------------------------------------------------------------------------------------
#DefineSubRoutine udsPrepareTestCase (intContestCase)
strCallFile1 = "20111216.HowTo.XML.MassReplace.1.wbt"
strCallFile2 = "20111218.HowTo.XML.MassReplace.2.wbt"
strCallFile3 = "20111219.HowTo.XML.MassReplace.3.wbt"
strCallFile4 = "20111220.HowTo.XML.MassReplace.4.wbt"
strCallFile5 = "20111220.HowTo.XML.MassReplace.5.wbt"
strCallFile6 = "20111220.HowTo.XML.MassReplace.6.wbt"
strCallFile7 = "20111223.HowTo.XML.MassReplace.7.wbt"
strContestant1 = strCallFile1 : " (StrIndexWild)"
strContestant2 = strCallFile2 : " (Binary Buffer)"
strContestant3 = strCallFile3 : " (DOM Extender)"
strContestant4 = strCallFile4 : " (Microsoft XML DOM)"
strContestant5 = strCallFile5 : " (Regular Expression)"
strContestant6 = strCallFile6 : " (FileRead)"
strContestant7 = strCallFile7 : " (Microsoft XML DOM XSLT)"
Switch intContestCase
Case 1
   blnresult = FileCopy ("Config.1.ini", "Config.ini", @FALSE)
   Display (3, "Config.ini", FileGet ("Config.ini"))
   Break
Case 2
   blnresult = FileCopy ("Config.2.ini", "Config.ini", @FALSE)
   Display (3, "Config.ini", FileGet ("Config.ini"))
   Break
EndSwitch
#EndSubRoutine
;------------------------------------------------------------------------------------------------------------------------------------------


;------------------------------------------------------------------------------------------------------------------------------------------
#DefineSubRoutine udsRunContestant (intContestant)
Exclusive (@ON)
Switch intContestant
Case 1
   arrContestants[intContestant] = strContestant1
   intStart = GetTickCount ()
   arrResult%intContestant% = Call (strCallFile1, "")
   intStop = GetTickCount ()
   arrContestTicks[intContestant] = arrContestTicks[intContestant] + intStop - intStart
   arrContestResults[intContestant] = udfArrayJoin (arrResult%intContestant%, " ")
   intLen%intContestant% = StrLen (arrContestResults[intContestant])
   Break

Case 2
   arrContestants[intContestant] = strContestant2
   intStart = GetTickCount ()
   arrResult%intContestant% = Call (strCallFile2, "")
   intStop = GetTickCount ()
   arrContestTicks[intContestant] = arrContestTicks[intContestant] + intStop - intStart
   arrContestResults[intContestant] = udfArrayJoin (arrResult%intContestant%, " ")
   intLen%intContestant% = StrLen (arrContestResults[intContestant])
   Break

Case 3
   arrContestants[intContestant] = strContestant3
   intStart = GetTickCount ()
   arrResult%intContestant% = Call (strCallFile3, "")
   intStop = GetTickCount ()
   arrContestTicks[intContestant] = arrContestTicks[intContestant] + intStop - intStart
   arrContestResults[intContestant] = udfArrayJoin (arrResult%intContestant%, " ")
   intLen%intContestant% = StrLen (arrContestResults[intContestant])
   Break

Case 4
   arrContestants[intContestant] = strContestant4
   intStart = GetTickCount ()
   arrResult%intContestant% = Call (strCallFile4, "")
   intStop = GetTickCount ()
   arrContestTicks[intContestant] = arrContestTicks[intContestant] + intStop - intStart
   arrContestResults[intContestant] = udfArrayJoin (arrResult%intContestant%, " ")
   intLen%intContestant% = StrLen (arrContestResults[intContestant])
   Break

Case 5
   arrContestants[intContestant] = strContestant5
   intStart = GetTickCount ()
   arrResult%intContestant% = Call (strCallFile5, "")
   intStop = GetTickCount ()
   arrContestTicks[intContestant] = arrContestTicks[intContestant] + intStop - intStart
   arrContestResults[intContestant] = udfArrayJoin (arrResult%intContestant%, " ")
   intLen%intContestant% = StrLen (arrContestResults[intContestant])
   Break

Case 6
   arrContestants[intContestant] = strContestant6
   intStart = GetTickCount ()
   arrResult%intContestant% = Call (strCallFile6, "")
   intStop = GetTickCount ()
   arrContestTicks[intContestant] = arrContestTicks[intContestant] + intStop - intStart
   arrContestResults[intContestant] = udfArrayJoin (arrResult%intContestant%, " ")
   intLen%intContestant% = StrLen (arrContestResults[intContestant])
   Break

Case 7
   arrContestants[intContestant] = strContestant7
   intStart = GetTickCount ()
   arrResult%intContestant% = Call (strCallFile7, "")
   intStop = GetTickCount ()
   arrContestTicks[intContestant] = arrContestTicks[intContestant] + intStop - intStart
   arrContestResults[intContestant] = udfArrayJoin (arrResult%intContestant%, " ")
   intLen%intContestant% = StrLen (arrContestResults[intContestant])
   Break

EndSwitch
Exclusive (@OFF)
#EndSubRoutine
;------------------------------------------------------------------------------------------------------------------------------------------


;------------------------------------------------------------------------------------------------------------------------------------------
#DefineFunction udfArrayJoin (arrArray, strDelimiter)
objJSC = CreateObject ("MSScriptControl.ScriptControl")
objJSC.Language = "JScript"
objJSC.AllowUI = @FALSE
Switch @TRUE
Case 256 == VarType (arrArray) ; WinBatch Array.
Case ObjectTypeGet (arrArray) == "ARRAY|VARIANT" ; Variant Array
   objJSC.AddCode(: "function VB2JSArray(objVBArray){var a;try{a=new VBArray(objVBArray).toArray();}catch(e){a=new Array(objVBArray);}return a;}")
   objJSC.AddCode(: "function ArrayJoin(objVBArray,strDelimiter){return VB2JSArray(objVBArray).join(strDelimiter);}")
   strJoined = objJSC.Run(: "ArrayJoin", arrArray, strDelimiter)
   Break
Case @TRUE
   strJoined = ""
EndSwitch
Return strJoined
;..........................................................................................................................................
; This UDF "udfArrayJoin" joins all elements of an array into a string.
; The elements will be separated by the specified delimiter string.
;
; Parameter:
; arrArray ....... A one-dimensional array of strings. Array type can be WinBatch Array or Variant Array.
; strDelimiter ... A single character or a string. The elements will be separated by this delimiter.
;..........................................................................................................................................
; (c)Detlev Dalitz.20100121.
; Jim Dippner.20080221: changed VB2JSArray.
; David Wang.20060704: created VB2JSArray.
;..........................................................................................................................................
#EndFunction
;------------------------------------------------------------------------------------------------------------------------------------------

;==========================================================================================================================================
Return ; from GoSub DEFINE_CONTEST_FUNCTIONS
;==========================================================================================================================================



;==========================================================================================================================================
:DEFINE_FUNCTIONS
;==========================================================================================================================================

;------------------------------------------------------------------------------------------------------------------------------------------
#DefineFunction udfArrayDumpToItemList (arrArray, intFirst, intLast, strDelimiter)
If !ArrInfo (arrArray, -1) Then Return "*ARRAY_IS_INVALID*" ; No Array, return invalid itemlist, i. e. empty string "".
If ArrInfo (arrArray, 0) != 1 Then Return "*ARRAY_IS_NOT_DIM_1*" ; Array is not a dim-1 array, return invalid itemlist, i. e. empty string "".
intElements = ArrInfo (arrArray, 1)
If intElements == 0 Then Return "*ARRAY_HAS_NO_ELEMENTS*" ; Array has no element.
intFirst = Min (Max (intFirst, 0), intElements - 1)
intLast = Min (Max (intLast, 0), intElements - 1)
strItemList = ""
intFixSize = StrLen (intLast)
For intI = intFirst To intLast
   If !!VarType (arrArray [intI])
      If arrArray [intI] == ""
         strItemList = ItemInsert (StrFixLeft (intI, "0", intFixSize) : "|" : "*ARRAY_ELEMENT_IS_EMPTY_STRING*", -1, strItemList, strDelimiter)
      Else
         arrArray [intI] = StrReplace (StrReplace (StrReplace (StrReplace (arrArray [intI], @CRLF, "@CRLF"), @CR, "@CR"), @LF, "@LF"), @TAB, "@TAB") ; Make WB style.
         arrArray [intI] = StrSub (arrArray [intI], 1, 200) ; Special truncation just for the small buffer of AskItemList.
         strItemList = ItemInsert (StrFixLeft (intI, "0", intFixSize) : "|" : arrArray [intI], -1, strItemList, strDelimiter)
      EndIf
   Else
      strItemList = ItemInsert (StrFixLeft (intI, "0", intFixSize) : "|" : "*ARRAY_ELEMENT_IS_UNDEFINED*", -1, strItemList, strDelimiter)
   EndIf
Next
IntControl (28, 1, 0, 0, 0)
IntControl (63, 050, 200, 950, 800)
Return AskItemlist ("Profiling|Preview Contestant Result", strItemList, strDelimiter, @UNSORTED, @SINGLE) ; This returns a Unicode string of VarType=128.
:CANCEL
Return @CANCEL
;..........................................................................................................................................
; This UDF "udfArrayDumpToItemList" reads a dim-1 array and returns an itemlist of all array cell items within an AskItemList dialog..
;
; Return values:
; "*ARRAY_IS_INVALID*"              ... Invalid array resp. this is no array.
; "*ARRAY_IS_NOT_DIM_1*"            ... Array is not a dim-1 array.
; "*ARRAY_HAS_NO_ELEMENTS*"         ... Array has no element.
; "*ARRAY_ELEMENT_IS_EMPTY_STRING*" ... Array element has vartype STRING but is empty.
; "*ARRAY_ELEMENT_IS UNDEFINED*"    ... Array element has undefined VarType.
; value                             ... Current value of the array element.
;
; Example: strItemList = udfArrayDumpToItemList (arrArray, 0, 19, @TAB)
;
; Detlev Dalitz.20090515.20100122.20101222.
;..........................................................................................................................................
#EndFunction
;------------------------------------------------------------------------------------------------------------------------------------------


;------------------------------------------------------------------------------------------------------------------------------------------
#DefineSubRoutine udsPrepareCounters ()
arrContestants = ArrDimension (1 + intContestantMax)    ; Array index 0 not used.
arrContestResults = ArrDimension (1 + intContestantMax) ; Array index 0 not used.
arrContestTicks = ArrDimension (1 + intContestantMax)   ; Array index 0 used for the sum.
arrContestPct = ArrDimension (1 + intContestantMax)     ; Array index 0 not used.
ArrInitialize (arrContestants, "")
ArrInitialize (arrContestResults, "")
ArrInitialize (arrContestTicks, 0)
ArrInitialize (arrContestPct, 0.0)
#EndSubRoutine
;------------------------------------------------------------------------------------------------------------------------------------------


;------------------------------------------------------------------------------------------------------------------------------------------
#DefineSubRoutine udsResultPerTestCase ()
Decimals (1)
For intContestant = intContestantMin To intContestantMax
   arrContestTicks[0] = arrContestTicks[0] + arrContestTicks[intContestant]
Next
intContestTicksMin = arrContestTicks[0]
For intContestant = intContestantMin To intContestantMax
   intContestTicksMin = Min (intContestTicksMin, arrContestTicks[intContestant])
Next
If arrContestTicks[0] < 1 Then arrContestTicks[0] = 1 ; To prevent dividing by zero.
For intContestant = intContestantMin To intContestantMax
   arrContestPct[intContestant] = 100.0 * arrContestTicks[intContestant] / arrContestTicks[0]
Next

; Format output.
strMsgTitle = "Performance Contest Result"
strTest = "Test"
strTicks = "Ticks"
strPct = "Pct"
strContestant = "Contestant"
strCase = "Contest Case = "
strIter = "Iterations = "
strSep = "  "
strPre = "; "
strWinner = "<== The Winner"
strDT = "DateTime = "
intLenTest = Max (StrLen (strTest), StrLen (intContestantMax))
intLenTicks = StrLen (strTicks)
intLenPct = StrLen (strPct)
intLenContestant = StrLen (strContestant)
intLenSep = StrLen (strSep)
intLenWinner = StrLen (strWinner)
For intContestant = intContestantMin To intContestantMax
   intLenTicks = Max (intLenTicks, StrLen (arrContestTicks[intContestant]))
   intLenPct = Max (intLenPct, StrLen (arrContestPct[intContestant]))
   intLenContestant = Max (intLenContestant, StrLen (arrContestants[intContestant]))
Next
intLenSum = intLenTest + intLenTicks + intLenPct + intLenContestant + intLenWinner + 4 * intLenSep
strTest = StrFixLeft (strTest, " ", intLenTest)
strTicks = StrFixLeft (strTicks, " ", intLenTicks)
strPct = StrFixLeft (strPct, " ", intLenPct)
strResult = strPre : StrFill ("-", intLenSum) : @LF : strPre : strMsgTitle
strResult = strResult : @LF : strPre : strCase : intContestCase
strResult = strResult : @LF : strPre : strIter : intContestLoopMax
strResult = strResult : @LF : strPre : strTest : strSep : strTicks : strSep : strPct : strSep : strContestant
For intContestant = intContestantMin To intContestantMax
   strTest = StrFixLeft (intContestant, " ", intLenTest)
   strTicks = StrFixLeft (arrContestTicks[intContestant], " ", intLenTicks)
   strPct = StrFixLeft (arrContestPct[intContestant], " ", intLenPct)
   strContestant = StrFix (arrContestants[intContestant], " ", intLenContestant)
   If arrContestTicks[intContestant] == intContestTicksMin Then strContestant = strContestant : strSep : strWinner
   strResult = strResult : @LF : strPre : strTest : strSep : strTicks : strSep : strPct : strSep : strContestant
Next
Return strResult : @LF : strPre : strDT : TimeYmdHms ()
#EndSubRoutine
;------------------------------------------------------------------------------------------------------------------------------------------

;==========================================================================================================================================
Return ; from GoSub DEFINE_FUNCTIONS
;==========================================================================================================================================

; -------------------------------------------------------------------------------------------------
; Performance Contest Result
; Contest Case = 1
; Iterations = 100
; Test   Ticks   Pct  Contestant
;    1   76150   6.3  20111216.HowTo.XML.MassReplace.1.wbt (StrIndexWild)
;    2   54671   4.5  20111218.HowTo.XML.MassReplace.2.wbt (Binary Buffer)
;    3   55285   4.5  20111219.HowTo.XML.MassReplace.3.wbt (DOM Extender)
;    4   14590   1.2  20111220.HowTo.XML.MassReplace.4.wbt (Microsoft XML DOM)
;    5    9248   0.8  20111220.HowTo.XML.MassReplace.5.wbt (Regular Expression)      <== The Winner
;    6  993066  81.6  20111220.HowTo.XML.MassReplace.6.wbt (FileRead)
;    7   14703   1.2  20111220.HowTo.XML.MassReplace.7.wbt (Microsoft XML DOM XSLT)
; DateTime = 2011:12:23:21:48:38
; -------------------------------------------------------------------------------------------------
; Performance Contest Result
; Contest Case = 2
; Iterations = 100
; Test   Ticks   Pct  Contestant
;    1  476009  26.7  20111216.HowTo.XML.MassReplace.1.wbt (StrIndexWild)
;    2  217914  12.2  20111218.HowTo.XML.MassReplace.2.wbt (Binary Buffer)
;    3   77191   4.3  20111219.HowTo.XML.MassReplace.3.wbt (DOM Extender)
;    4   17574   1.0  20111220.HowTo.XML.MassReplace.4.wbt (Microsoft XML DOM)
;    5   19645   1.1  20111220.HowTo.XML.MassReplace.5.wbt (Regular Expression)
;    6  963121  53.9  20111220.HowTo.XML.MassReplace.6.wbt (FileRead)
;    7   14241   0.8  20111220.HowTo.XML.MassReplace.7.wbt (Microsoft XML DOM XSLT)  <== The Winner
; DateTime = 2011:12:23:22:18:35
; -------------------------------------------------------------------------------------------------