AutoHotkey Expression Examples: "" %% () and all that.
because I can never get them right, so I made this. These are all working examples.   Version 1.21c  08/24/2009

CONTENTS:

A:RETRIEVING COMMAND LINE PARAMETERS
B:COMMON THINGS AT THE BEGINNING AND END OF AUTOHOTKEY SCRIPTS
C:WHEN TO USE %% AROUND VARIABLES
D:ERASE A VARIABLE
E:SET A VARIABLE   :=   [store numbers, quoted strings]
F:SET A VARIABLE      [assign unquoted literal strings]
G:COPY A VARIABLE
H:IF STATEMENTS with ()
H2: Comparing Numeric Values vs. Comparing Strings
I:IF STATEMENTS without () [Translate the 1st, take the 2nd literally]
I2: Comparing Numeric Values vs. Comparing Strings
J:CHECK FOR A BLANK VARIABLE
K:STRING MANIPULATION
K1:Trim whitespace at the start of the string
K2:Trim whitespace at the end of the string
K3:Trim whitespace at the start and the end of the string
K4:Concatenate two strings together
K5:Two ways of using MsgBox
L:NUMBERS
L1:Adding numbers together
L2:Adding two strings together:
when both can be interpreted as integers, gives the resulting integer (as a string)
when both can be interpreted as float, gives the resulting float (as a string)
when one or both can NOT be interpreted as a number, result is an empty string
L3:Remove leading and trailing blanks and leading zeros from a number
L4:Various ways to pad a number with leading zeros or spaces
M:working with FILE NAMES
N:REGULAR EXPRESSIONS
N1:Links to: Cheat Sheets, documentation, programs, libraries
N2:Examples
N3:RegExReplace
N3.1: Examples
N3.2: Extract Month, Day, Year, from 1/22/2009
N3.3: An example of how we can step by step build up our Regular Expression
N3.4: Find the $ dollar sign. Extract price and add a dollar sign.
O:MISC AUTOHOTKEY NOTES. CAVEATS & DEBUGGING TIPS
O1:Notes / Caveats
O2:Sending debug data to a log file
O3:Capturing a screen image during run
P:MISC AUTOHOTKEY SCRIPTS
P1:Misc AutoHotkey Scripts
P2:Index of notable scripts found in the AutoHotkey Forum
P3:AHK Functions - ()
P4:Library for Text File Manipulation
P5:Tray Icons
P6:Force Exit another AutoHotkey script
Q:NAVIGATING WEB SITES
Q1:Determining when a webpage has finished loading
Q2:Positioning on a control
Q3:Search for a certain colored pixel
R:NEWBIE RECOMMENDED LEARNING SEQUENCE
S:Press ESC to cancel this scipt
T:THE AUTOHOTKEY RUN COMMAND
U:PASSING PARAMETERS TO AUTOHOTKEY SCRIPTS
V:PASSING PARAMETERS TO ANY PROGRAM



/******************************************************************************
NOTE:  ALL VARIABLES ARE STORED AS CHARACTER STRINGS !!!
Strings containing numbers are converted to numbers when needed, and the result is converted back to a string.
/******************************************************************************
NOTE:  Closing */ must be first thing on line. Otherwise you'll be asking yourself, "Why does my script stop running at this point, as if the whole rest of the script was commented out?"



/******************************************************************************
A:  PASSING COMMAND LINE PARAMETERS TO AN AUTOHOTKEY SCRIPT
A:  RETRIEVING COMMAND LINE PARAMETERS
NumParams = %0%
Param1 = %1%
Param2 = %2%
Param3 = %3%
MsgBox NumParams = %0%
MsgBox Param1 = %1%
MsgBox Param2 = %2%
MsgBox Param3 = %3%


/******************************************************************************
B:  COMMON THINGS OFTEN FOUND AT THE BEGINNING OF AUTOHOTKEY SCRIPTS
#NoTrayIcon              ;if you don't want a tray icon for this AutoHotkey program.
#NoEnv                   ;Recommended for performance and compatibility with future AutoHotkey releases.
#SingleInstance force    ;Skips the dialog box and replaces the old instance automatically
;;SendMode Input           ;I discovered this causes MouseMove to jump as if Speed was 0. (was Recommended for new scripts due to its superior speed and reliability.)
SetKeyDelay, 90          ;Any number you want (milliseconds)
CoordMode,Mouse,Screen   ;Initial state is Relative
CoordMode,Pixel,Screen   ;Initial state is Relative. Frustration awaits if you set Mouse to Screen and then use GetPixelColor because you forgot this line. There are separate ones for: Mouse, Pixel, ToolTip, Menu, Caret
MouseGetPos, xpos, ypos  ;Save initial position of mouse
WinGet, SavedWinId, ID, A     ;Save our current active window

;Set Up a Log File:
SetWorkingDir, %A_ScriptDir%  ;Set default directory to where this script file is located. (Note %% because it's expecting and unquoted string)
LogFile := "MyLog.txt"
FileAppend, This is a message`n, %LogFile%  ;Note the trailing (`n) to start a new line. This could instead be a leading (`n) if you want. (Note %% because it's expecting and unquoted string)
and things at the end where we restore window and mouse cursor position:
WinActivate ahk_id %SavedWinId%  ;Restore original window
MouseMove, xpos, ypos, 10    ;Restore original mouse position
ExitApp
Esc::ExitApp  ;Press ESC to cancel this script. Placed after the ExitApp.
              ;Note this is a hotkey definition (we're defining the ESC key to run ExitApp). A
              ;hotkey definition line stops execution at that point, so if you want the script
              ;to run to the end but have the ESC key available to terminate the script, put
              ;the hotkey definition at the end, just after your ExitApp statement.




/******************************************************************************
C:  WHEN TO USE %% AROUND VARIABLES

LESSON #1:
The only place to use %x% is where a literal string NOT enclosed in double-quotes is expected. Otherwise, don't use %% around a variable name.

Notice in the following examples that unquoted literal strings are expected.
( = assigns unquoted literal strings )

n = Ishmael
x = Call me %n%
MsgBox %x%

x = 500
y = 500
z = 10
MouseMove, 500, 500, 10           ;works
MouseMove, 500 - 1, 500 + 1, 10   ;works
MouseMove,  x, y, z               ;works
MouseMove,  x - 1, y + 1, z + 2   ;works

;However, this doesn't work, because MouseMove
;doesn't expect an unquoted literal string
MouseMove, %x% - 1, %y% + 1, 10   ;doesn't work
    Confusion is caused because the following also happens to work:
MouseMove, %x%, %y%, %c%   ;works because "for backward compatibility, command parameters that are
                           ;documented as 'can be an expression' treat an isolated name in percent signs
                           ;(e.g. %Var%, but not Array%i%) as though the percent signs are absent."
                           ;        --AutoHotkey Documentation: Variables and Expressions

LESSON #2:
Use (%x%) (enclosed in parentheses) when x contains the name of a 2nd variable which in turn contains the contents you want.
a = 500    ;a = "500"
b = 200    ;b = "200"
x := "a"
y := "b"
MouseMove, (%x%), (%y%)            ;x = a, a = 500.  y = b, b = 200
MouseGetPos, xpos, ypos
MsgBox xpos=%xpos%  ypos=%ypos%    ;xpos=500  ypos=200

LESSON #3:
Instances which look like exceptions to the rule:
MyDocument := "C:\Program Files\AutoHotkey\license.txt"
Run, notepad.exe "%MyDocument%"
Looks like we're using %% inside a quoted string, but actually the "" are not required, just recommended. This happens to also work:
Run, notepad.exe %MyDocument%
The run function expects an unquoted string, so we use %%, otherwise notepad would try to open a file named 'MyDocument'.

In the first case above, the run function is actually accepting an unquoted string which happens to begin and end with a double quote character.


Tech Note
I believe the Target string in the AutoHotkey Run command is passed as the command_line parameter to the Windows CreateProcess() function. I see in AutoHotkey source file script.cpp routine Script::ActionExec the call to CreateProcess is:
if (CreateProcess(NULL, command_line, NULL, NULL, FALSE, 0, NULL, aWorkingDir, &si, &pi))
MSDN documentaion for CreateProcess says, "If you are using a long file name that contains a space, use quoted strings to indicate where the file name ends and the arguments begin."

So the beginning and ending double quote characters are actually a part of the string being passed.

(05/29/2009 — I'm testing how AutoHotkey parses the Run command. I'll post the results when I'm done.)

Reference:
    CreateProcess() : http://msdn.microsoft.com/en-us/library/ms682425.aspx
    CreateProcess() : http://msdn.microsoft.com/en-us/library/ms682425(VS.85).aspx


/******************************************************************************
D:  ERASE A VARIABLE
v =
v := ""


/******************************************************************************
E:  SET A VARIABLE (:=)
Use the colon-equal operator (:=) for storing numbers and quoted strings

NOTE: All variables including numbers are stored as character strings. Strings are automatically converted to numbers when necessary, then converted back to strings when result is stored in a variable.
ABC := "David"
David := "Susan"

v := "ABC"                      ; v = "ABC"
MsgBox v := "ABC"`n`nv = "%v%"

v := ABC                        ; ABC is a variable. v = "David"
MsgBox v := ABC`n`nv = "%v%"

v := %ABC%                      ; ABC is a variable containing the name of a variable. v = "Susan"
MsgBox v := `%ABC`%`n`nv="%v%"  ; NOTE: If ABC is undefined or blank, program halts!

v := "123"                      ; v = "123" (quotes NOT included)
MsgBox v := "123"`n`nv = "%v%"

v := 123                        ; v = "123" (If it can be interpreted as a number then it's a number, otherwise it's a variable name.)
MsgBox v := 123`n`nv = "%v%"

;123 can be made into a variable, as in this horrendous example:
123 := 456
MsgBox v = %123%  ; message is "v = 456"



/******************************************************************************
F:  SET A VARIABLE (=)
equal sign operator (=) to assign unquoted literal strings
To include variable ABC instead of literal string "ABC", use %ABC%
ABC = David
David = Susan

v =  123                        ;v = "123"
MsgBox v = 123`n`nv = "%v%"

v = 0001                        ;v = "0001"
MsgBox v = 0001`n`nv = "%v%"

v = ABC                         ;v = "ABC"
MsgBox v = ABC`n`nv = "%v%"

v = %ABC%                       ;ABC is a variable. v = "David"
MsgBox v = `%ABC`%`n`nv = "%v%" (ABC = "David")

;PROBABLY NOT WHAT YOU WANTED:
v = "ABC"                       ;v = the literal string "ABC" (including double-quotes)
MsgBox v = "ABC"`n`nv = '%v%'



/******************************************************************************
G:  COPY A VARIABLE
ABC := "David"
David := "Susan"

v := ABC                        ; ABC is a variable. v = "David"
MsgBox v := ABC`n`nv = "%v%"
v = %ABC%                       ; ABC is a variable. v = "David"
MsgBox v = `%ABC`%`n`nv = "%v%"

;PROBABLY NOT WHAT YOU WANTED:
v = ABC                         ; v = "ABC" (the literal string)
MsgBox v = ABC`n`nv = "%v%"
v := %ABC%                      ; ABC is a variable containing the name of a variable. v = "Susan"
MsgBox v := `%ABC`%`n`nv="%v%"  ; NOTE: If ABC is undefined, PROGRAM HALTS!
                                        (If David is undefined, then v = "")



/******************************************************************************
H:  IF STATEMENTS with ()
SAT := "Saturday"          ;Another way to view this is:
Saturday := "Saturn"       ;  SAT --> Saturday --> Saturn
MON := "Monday"            ;  MON --> Monday --> Moon
Monday := "Moon"

MsgBox SAT := "Saturday"`nSaturday := "Saturn"`nMON := "Monday"`nMonday := "Moon"`n`n(another way to view this:)`nSAT --> Saturday --> Saturn`nMON --> Monday --> Moon`n`n#16

; =
If ("Saturday" = "Saturday")
  MsgBox ("Saturday" = "Saturday")
If ("Saturday" = "SATURDAY")
  MsgBox ("Saturday" = "SATURDAY")

; ==  (case sensitive compare)
If ("Saturday" == "Saturday")              ;== Case Sensitive
  MsgBox ("Saturday" == "Saturday")
If ("Saturday" == "SATURDAY")              ;== Case Sensitive
  MsgBox NO

;SAT = "Saturday"
If (SAT = "Saturday")       ;SAT = "Saturday", compare with "Saturday"
  MsgBox (SAT = "Saturday")
If ("Saturday" = SAT)       ;Reverse works the same
  MsgBox ("Saturday" = SAT)
If (SAT = "xxxxx")
  MsgBox NO
If ("xxxxx" = SAT)
  MsgBox NO

;%SAT% = "Saturn"
If ("Saturn" = "Saturn")
  MsgBox ("Saturn" = "Saturn")
If (%SAT% = "Saturn")  ;SAT = "Saturday", %SAT% = "Saturn", compare with "Saturn" (no problem if SAT not defined)
  MsgBox (`%SAT`% = "Saturn")`n`n(no problem if SAT not defined)
If ("Saturn" = %SAT%)  ;Reverse works the same (no problem if SAT not defined)
  MsgBox ("Saturn" = `%SAT`%)`n`n(no problem if SAT not defined)
If ("xxxxx" = %SAT%)   ;compare "xxxxx" with "Saturn"
  MsgBox NO
If (%SAT% = "xxxxx")   ;compare "Saturn" with "xxxxx"
  MsgBox NO

;"Moon" = %MON%
If ("Moon" = "Moon")
  MsgBox ("Moon" = "Moon")
If (%MON% = "Moon")    ;MON = "Monday", Monday = "Moon", compare with "Moon" (no problem if MON not defined)
  MsgBox (%MON% = "Moon")`n`nMON = "Monday", Monday = "Moon", compare with "Moon"`n`n(no problem if MON not defined)
If ("Moon" = %MON%)    ;"Moon", compare with MON = "Monday", Monday = "Moon" (no problem if MON not defined)
  MsgBox ("Moon" = `%MON`%)`n`n"Moon", compare with MON = "Monday", Monday = "Moon"`n`n(no problem if MON not defined)
If ("xxxxx" = %MON%)   ;compare "xxxxx" with "Moon"
  MsgBox NO
If (%MON% = "xxxxx")   ;compare "Moon" with "xxxxx"
  MsgBox NO

;SAT =? MON
If (SAT = MON)      ;Compare "Saturday" = "Monday" [SAT = "Saturday", MON = "Monday"]
  MsgBox NO
If (SAT < MON)      ;"Saturday" < "Moon"
  MsgBox NO
If (SAT > MON)      ;"Saturday" > "Moon"  [S > M]
  MsgBox (SAT > MON)`n`n"Saturday" > "Monday"`n`n[S > M]

;SAT =? %MON%
If (SAT = %MON%)    ;Compare "Saturday" = "Moon". [SAT = "Saturday", compare with MON = "Monday", Monday = "Moon"]
  MsgBox NO
If (SAT < %MON%)    ;"Saturday" < "Moon"
  MsgBox NO
If (SAT > %MON%)    ;"Saturday" > "Moon"  [S > M]
  MsgBox (SAT > `%MON`%)`n`n"Saturday" > "Moon"   [S > M]`n`nSAT = "%SAT%",`nMON = "%MON%", %MON% = "Moon"

;%SAT% =? MON
If (%SAT% = MON)    ;Compare "Saturn" = "Monday". [SAT = "Saturday", Saturday = "Saturn", MON = "Monday"]
  MsgBox NO
If (%SAT% < MON)    ;"Saturn" < "Monday"
  MsgBox NO
If (%SAT% > MON)    ;"Saturn" > "Monday"  [S > M]
  MsgBox (`%SAT`% > MON)`n`nSAT = "Saturday", %SAT% = "Saturn", compare with MON = "Monday"`n`n"Saturn" > "Moon"`n`n[S > M]

;%SAT% =? %MON%
If (%SAT% = %MON%)  ;Compare "Saturn" = "Moon". [SAT = "Saturday", Saturday = "Saturn", compare with MON = "Monday", Monday = "Moon"]
  MsgBox NO
If (%SAT% < %MON%)  ;"Saturn" < "Moon"
  MsgBox NO
If (%SAT% > %MON%)  ;"Saturn" > "Moon"  [S > M]
  MsgBox (`%SAT`% > `%MON`%)`n`nSAT = "Saturday", %SAT% = "Saturn", compare with`nMON = "Monday", %MON% = "Moon"`n`n"Saturn" > "Moon"`n`n[S > M]

H2: Comparing Numeric Values vs. Comparing Strings
If they can both be interpreted as numbers, then they are compared as numbers. Otherwise they are compared as strings.
;COMPARING NUMERIC VALUES VS. COMPARING STRINGS     if statements with ()
x = 05           ; x = "05"
if (x > 3.14)    ; (5 > 3.14) ?  Compare numeric values, since both can be interpreted as numeric values.
  MsgBox if (x > 3.14)`nwith x = "05"`n`nCompare numeric values, since both "05" and "3.14" can be interpreted as numbers.`n(5 > 3.14) ?`nyes
else
  MsgBox xxxxxx

if (x > "3.14")  ; ("05" > "3.14") ?  Compare strings, since "3.14" is explicitly a string. (The " " around 3.14 say it's a string, not a number, so do a string compare.)
  MsgBox xxxxxx
else
  MsgBox if (x > "3.14")`nwith x = "05"`n`nCompare strings, since "3.14" is explicitly a string.`nThe " " around "3.14" say it's a string, not a number, so do a string compare.`n("05" > "3.14") ?`n("0" > "3") ?`n(48 > 51) ?`nno


; ASCII table:
;   /  47
;   0  48
;   1  49
;   2  50
;   3  51
;   4  52
;   5  53
;   6  54
;   7  55
;   8  56
;   9  57
;   :  58
;DEREFERENCE TESTS
y := "x"

;Compare %y% with 3.14
x = 03             ; x = "03"
if (%y% > 3.14)    ; (3 > 3.14) ?
  MsgBox xxxxxx
else
  MsgBox if (`%y`% > 3.14)`nwith y = "x"`nand x = "03"`n`nCompare numeric values, since both "03" and "3.14" can be interpreted as numbers.`n(3 > 3.14) ?`nno

x = 05             ; x = "05"
if (%y% > 3.14)    ; (5 > 3.14) ?
  MsgBox if (`%y`% > 3.14)`nwith y = "x"`nand x = "05"`n`nCompare numeric values, since both "05" and "3.14" can be interpreted as numbers.`n(5 > 3.14) ?`nyes
else
  MsgBox NO

;Compare %y% with "3.14"
x = 03               ; x = "03"
if (%y% > "3.14")    ; ("03" > "3.14") ?
  MsgBox xxxxxx
else
  MsgBox if (`%y`% > "3.14")`nwith y = "x"`nand x = "03"`n`nCompare strings, since "3.14" is explicitly a string.`nThe " " around "3.14" say it's a string, not a number, so do a string compare.`n("03" > "3.14") ?`n("0" > "3") ?`n(48 > 51) ?`nno

x = 05               ; x = "05"
if (%y% > "3.14")    ; ("05" > "3.14") ?
  MsgBox xxxxxx
else
  MsgBox if (`%y`% > "3.14")`nwith y = "x"`nand x = "05"`n`nCompare strings, since "3.14" is explicitly a string.`nThe " " around "3.14" say it's a string, not a number, so do a string compare.`n("05" > "3.14") ?`n("0" > "3") ?`n(48 > 51) ?`nno

x := "/"             ; x = "/"
if (%y% > "3.14")    ; ("/" > "3.14") ?
  MsgBox xxxxxx
else
  MsgBox if (`%y`% > "3.14")`nwith y = "x"`nand x = "/"`n`nCompare strings, since "3.14" is explicitly a string.`nThe " " around "3.14" say it's a string, not a number, so do a string compare.`n("/" > "3.14") ?`n("/" > "3") ?`n(47 > 51) ?`nno

x := ":"             ; x = ":"
if (%y% > "3.14")    ; (":" > "3.14") ?
  MsgBox if (`%y`% > "3.14")`nwith y = "x"`nand x = ":"`n`nCompare strings, since "3.14" is explicitly a string.`nThe " " around "3.14" say it's a string, not a number, so do a string compare.`n(":" > "3.14") ?`n(":" > "3") ?`n(58 > 51) ?`nyes
else
  MsgBox xxxxxx



/******************************************************************************
I:  IF STATEMENTS without ()
Translate the 1st, take the 2nd literally
SAT := "Saturday"          ;Another way to view this is:
Saturday := "Saturn"       ;  SAT --> Saturday --> Saturn
MON := "Monday"            ;  MON --> Monday --> Moon
Monday := "Moon"

MsgBox SAT := "Saturday"`nSaturday := "Saturn"`nMON := "Monday"`nMonday := "Moon"`n`n(another way to view this:)`nSAT --> Saturday --> Saturn`nMON --> Monday --> Moon

;SAT
; If "Saturday" = .... illegal
If SAT = Saturday    ;SAT = "Saturday", compare with "Saturday"
  MsgBox If SAT = Saturday`n`nSaturday = Saturday
If SAT = %Saturday%  ;SAT = "Saturday", compare with %Saturday% = "Saturn"
  MsgBox NO
If SAT = SAT         ;SAT = "Saturday", compare with "SAT"
  MsgBox NO
If SAT = %SAT%       ;SAT = "Saturday", compare with %SAT% = "Saturday"
  MsgBox If SAT = `%SAT`%`n`nSaturday = Saturday

;%SAT%
;NOTE: if SAT is undefined or blank, program will halt!
If %SAT% = Saturn   ;SAT = "Saturday", Saturday = "Saturn", compare with "Saturn"
  MsgBox If `%SAT`% = Saturn`n`nSAT = "%SAT%", `%Saturday`% = %Saturday%, compare with "Saturn"`n`n(Note: if SAT is undefined or blank, program will halt!)
If %SAT% = xxxxx   ;SAT = "Saturday", Saturday = "Saturn", compare with "xxxxx"
  MsgBox NO

;Saturday
If Saturday = Saturn   ;Saturday = "Saturn", compare with "Saturn"
  MsgBox Saturday = Saturn`n`nSaturday="%Saturday%",compare with "Saturn"
If Saturday = xxxxx   ;Saturday = "Saturn", compare with "xxxxx"
  MsgBox NO

;%Saturday%
;NOTE: if SATURDAY is undefined or blank, program will halt!
If %Saturday% =       ;Saturday = "Saturn", Saturn = <nothing>, compare with <nothing>
  MsgBox If `%Saturday`% = `n`nSaturday=%Saturday%, Saturn=<nothing>, compare with <nothing>`n`n(NOTE: if SATURDAY is undefined or blank, program will halt!)
If %Saturday% = %Saturn%  ;Saturday = "Saturn", Saturn = <nothing>, compare with %Saturn% = <nothing> (<nothing> = <nothing>)
  MsgBox if `%Saturday`% = `%Saturn`%`n`nSaturday=%Saturday%, Saturn=<nothing>`ncompare with`%Saturn`% = <nothing>`n`n<nothing>=<nothing>
If %Saturday% = xxxxx ;Saturday = "Saturn", Saturn = <nothing>, compare with "xxxxx"
  MsgBox NO
If %Saturday% = ""    ;Saturday = "Saturn", Saturn = <nothing>, compare with literal two double-quotes (a string containing two characters, both double-quotes)
  MsgBox NO

I2: Comparing Numeric Values vs. Comparing Strings
If they can both be interpreted as numbers, then they are compared as numbers. Otherwise they are compared as strings.
I2:
;COMPARING NUMERIC VALUES VS. COMPARING STRINGS     if statements without ()
; ASCII table:
;   !  33
;   "  34
;   #  35
;   0  48

x = 03            ; x = "03"
if x > 3.14       ; 3 > 3.14  (Compare numeric values, since both can be interpreted as numeric values)
  MsgBox xxxxxx
else
  MsgBox if x > 3.14`nwith x=%x%`n`nCompare numeric values, since both can be interpreted as numeric values`n3 > 3.14 ?`nno

x = 05            ; x = "05"
if x > 3.14       ; 5 > 3.14  (Compare numeric values, since both can be interpreted as numeric values)
  MsgBox if x > 3.14`nwith x=%x%`n`nCompare numeric values, since both can be interpreted as numeric values`n5 > 3.14 ?`nyes
else
  MsgBox xxxxxx

x = 03            ; x = "03"
if x > "3.14"     ; compare string '03' with string '"3.14"' (double quotes are part of the string). Compare ascii 0 in 03 with leading quotation mark in "3.14" (48 > 34 ?) Yes.
  MsgBox if x > "3.14"`nwith x=%x%`n`nDouble quotes are part of the string "3.14"`nso string compare 03 with "3.14"`ncompare leading '0' in 03 with leading quotation mark in "3.14"`nascii(0) = 48`nascii(") = 34`n48 > 34 (?)`nyes
else
  MsgBox xxxxxx

x = !             ; x = '!' (ascii 33)
if x > "3.14"     ;compare string '!' with string '"3.14"' (double quotes are part of the string). Compare ascii ! with leading quotation mark in "3.14" (48 > 34 ?) Yes.
; (! > ")?  --> (33 > 34) ? no
  MsgBox xxxxxx
else
 MsgBox if x > "3.14"`nwith x=%x%`nno`n`ncompare ascii ! with leading quotation mark in "3.14"`nascii(!) = 33`nascii(") = 34`n(33 > 34)?`nno

x = #             ; x = '#' (ascii 35)
if x > "3.14"     ; (! > ")?  --> (35 > 34) ? yes
  MsgBox if x > "3.14"`nwith x=%x%`nyes`n`ncompare ascii # with leading quotation mark in "3.14"`nascii(#) = 35`nascii(") = 34`n(35 > 34)?`nyes
else
  MsgBox xxxxxx


; ASCII table:
;   !  33
;   "  34
;   #  35
;   0  48
;DEREFERENCE TESTS
y := "x"

;compare %y% with 3.14
x = 03            ; x = "03"
if %y% > 3.14     ; 3 > 3.14 (?)
  MsgBox xxxxxx
else
  MsgBox if `%y`% > 3.14`nwith y := "x"`nand x = "03"`n`nCompare numeric values, since both "03" and "3.14" can be interpreted as numbers.`n3 > 3.14 (?)`nno

x = 05            ; x = "05"
if %y% > 3.14     ; 5 > 3.14 (?)
  MsgBox if `%y`% > 3.14`nwith y := "x"`nand x = "05"`n`nCompare numeric values, since both "05" and "3.14" can be interpreted as numbers.`n5 > 3.14 (?)`nyes
else
  MsgBox xxxxxx


;compare %y% with "3.14"
x = 03            ; x = "03"
if %y% > "3.14"   ; Double quotes are part of the string "3.14" so string compare '03' with string '"3.14"'. Compare ascii 0 in 03 with leading quotation mark in "3.14" (48 > 34 ?) Yes.
  MsgBox if `%y`% > "3.14"`nwith y := "x"`nand x=%x%`n`nDouble quotes are part of the string "3.14"`nso string compare 03 with "3.14"`ncompare leading '0' in 03 with leading quotation mark in "3.14"`nascii(0) = 48`nascii(") = 34`n48 > 34 (?)`nyes
else
  MsgBox xxxxxx

x = !             ; x = '!' (ascii 33)
if x > "3.14"     ;Double quotes are part of the string "3.14" so string compare '!' with string '"3.14"'. Compare '!' with leading quotation mark in "3.14" (48 > 34 ?) Yes.
  MsgBox xxxxxx
else
  MsgBox if `%y`% > "3.14"`nwith y := "x"`nand x=%x%`n`nDouble quotes are part of the string "3.14"`nso string compare ! with "3.14"`ncompare '!' with leading quotation mark in "3.14"`nascii(!) = 33`nascii(") = 34`n33 > 34 (?)`nno

x = #             ; x = '#' (ascii 35)
if x > "3.14"     ; (! > ")?  --> (35 > 34) ? yes
  MsgBox if `%y`% > "3.14"`nwith y := "x"`nand x=%x%`n`nDouble quotes are part of the string "3.14"`nso string compare # with "3.14"`ncompare '#' with leading quotation mark in "3.14"`nascii(#) = 35`nascii(") = 34`n35 > 34 (?)`nyes
else
  MsgBox xxxxxx



/******************************************************************************
J:  CHECK FOR A BLANK VARIABLE
(or undefined variable)
v := ""

If v =
  MsgBox v = ""

If (v = "")
  MsgBox v = ""



/******************************************************************************
K:  STRING MANIPULATION

K1: Trim whitespace at the START of a string
;Trim whitespace at the START of a string:
v := "     0001     "
MsgBox v="%v%"
v := RegExReplace( v, "\A\s+" )
MsgBox v="%v%"                  ;v = "0001     "

K2: Trim whitespace at the END of a string
;Trim whitespace at the END of a string:
v := "     0001     "
MsgBox v="%v%"
v := RegExReplace( v, "\s+\z" )
MsgBox v="%v%"                  ;v = "     0001"


K3: Trim whitespace at the START AND END of a string
K3a:
;Trim whitespace at the START AND END of a string:
v := "     0001     "
MsgBox v="%v%"
v := RegExReplace( v, "(^\s+)|(\s+$)")
MsgBox v="%v%"                  ;v = "0001"
K3b:
;Trim whitespace at the START AND END of the string:
v := "     0001     "
MsgBox v="%v%"
v = %v%                         ;v = "0001" (AutoTrim ON by default)
MsgBox v="%v%"


K4: Concatenate Two Strings Together
;CONCATENATE TWO STRINGS TOGETHER
SAT := "Saturday"
MON := "Monday"
Saturday := "Saturn"
Monday := "Moon"


; using =
v = %SAT%%MON%      ; v = "SaturdayMonday"
MsgBox v = "%v%"


; using :=
v := "Saturday" . "Monday"  ; v = "SaturdayMonday"
MsgBox v = "%v%"

v := SAT . MON      ; v = "SaturdayMonday" (there must be a SPACE before and after dot)
MsgBox v = "%v%"

v := %SAT% . MON    ; v = "SaturnMonday"
MsgBox v = "%v%"

v := SAT . %MON%    ; v = "SaturdayMoon"
MsgBox v = "%v%"

v := %SAT% . %MON%  ; v = "SaturnMoon"
MsgBox v = "%v%"


K5: Two ways of using MsgBox
This is a good place to mention the two ways of using MsgBox:
Msgbox Var = %Var%
; OR
Msgbox % "Var = " . Var
;  string-^^^^^^  | ^^^-variable name
;           Concatenate

K6:
SEE ALSO:
    Library for Text File Manipulation
    http://www.autohotkey.net/~heresy/Functions/TXT.ahk


/******************************************************************************
L:  NUMBERS
NOTE: All variables are stored as character strings.
Strings are automatically converted to numbers when necessary,
then converted back to strings when result is stored in a variable.

L1: Adding numbers together
;Adding numbers together
v := "123"
v += 1
MsgBox v = "%v%"     ; v <- "124"

v := "123"
v := v + 1
MsgBox v = "%v%"     ; v <- "124"

;PROBABLY NOT WHAT YOU WANTED:
v = 123            ; v <- "123" (the literal string)
v = v + 1          ; v <- "v + 1" (the literal string)
MsgBox v = "%v%"

L2: Adding two strings together
;Adding two strings together
;when both can be interpreted as integers, gives the resulting integer (as a string)
v1 := 123
v2 := 456
v := v1 + v2       ; v <- "579"
MsgBox v = "%v%"

;when one or both can be interpreted as float, gives the resulting float (as a string)
v1 := 1.23
v2 := 45.6
v := v1 + v2       ; v <- "46.830000"
MsgBox v = "%v%"

;When one or both can NOT be interpreted as a number, result is an empty string
v1 := "123"
v2 := "Susan"
v := v1 + v2       ; v <- "" (empty string)
MsgBox v = "%v%"

L3: Remove leading/trailing blanks/zeros from a number
;Remove leading zeros from a number
v := 0001             ;v = "0001"
v += 0                ;v converted to integer, add zero, convert back to string
MsgBox v = "%v%"      ;v = "1" (the literal string "1"

;Remove leading blanks and trailing blanks from a number
v := "     1     "
MsgBox v = "%v%"      ;v = "     1     "
v += 0                ;v converted to integer, add zero, convert back to string
MsgBox v = "%v%"      ;v = "1" (the literal string "1"

;Remove leading and trailing blanks and leading zeros from a number
v := "     0001     "
MsgBox v = "%v%"      ;v = "     0001     "
v += 0                ;v converted to integer, add zero, convert back to string
MsgBox v = "%v%"      ;v = "1" (the literal string "1"

;(yea it's all the same. Just do v += 0)

L4: Pad a number with leading zeros or spaces
/************************************************
VARIOUS WAYS TO PAD A NUMBER WITH LEADING ZEROS OR SPACES
(To pad with spaces, substitute spaces for the zeros.)

L4.1: Method #1: SubStr
;PAD A NUMBER WITH LEADING ZEROS OR SPACES — Method #1: SUBSTR
; Documentation on SubStr: "If StartingPos is less than 1, it is
; considered to be an offset from the end of the string. For example, 0
; extracts the last character and -1 extracts the two last characters."
v := 123
            ;....v....1                   ....v....1
v := SubStr("0000000000" . v, -9)  ; v = "0000000123"
MsgBox v = "%v%"

v := SubStr("abcdefghij" . v, -9)  ; v = "defghij123"  (easier to see what's happening)
MsgBox v = "%v%"

L4.2: Method #2: StringRight
;PAD A NUMBER WITH LEADING ZEROS OR SPACES — Method #2: StringRight
v := 123
     ;....v....1              ....v....1...
v := "0000000000" . v  ; v = "0000000000123"  ( or could use v = "0000000000"%v% )
StringRight, v, v, 10  ; v =    "0000000123"
MsgBox v = "%v%"

L4.3: Method #3: sprintf()
;PAD A NUMBER WITH LEADING ZEROS OR SPACES — Method #3: sprintf()
StrIn := "1234"
size := VarSetCapacity(StrOut, 8)  ;want StrOut to hold 8 digits

;pad with zeros
DllCall("msvcrt\sprintf", Str, StrOut, Str, "%08d", "Int", StrIn )  ;pad with zeros
MsgBox, 0, Zeros, size=%size%`nStrIn = %StrIn%`nStrOut = %StrOut%   ;StrOut = "00000123"

;pad with blanks
DllCall("msvcrt\sprintf", Str, StrOut, Str,  "%8d", "Int", StrIn )  ;pad with blanks
MsgBox, 0, Spaces, size=%size%`nStrIn = %StrIn%`nStrOut = %StrOut%  ;StrOut = "     123"

L4.4: Method #4: Prepend leading zeros
;PAD A NUMBER WITH LEADING ZEROS OR SPACES — Method #4: Prepend leading zeros
v = 123
Loop, % 9-StrLen(v)            ; (9 for 9 digits total)
    v = 0%v%                   ; OR: v := 0 . v
MsgBox, 0, Zeros, v = "%v%"    ; v = "000000123"

;Prepend leading spaces
v = 123
Loop, % 9-StrLen(v)            ; (9 for 9 digits & spaces total)
    v := A_Space . v         ; OR: v := " " . v
MsgBox, 0, Spaces, v = "%v%"   ; v = "      123"

L4.5: Method #5: SetFormat
;PAD A NUMBER WITH LEADING ZEROS OR SPACES — Method #5: Using SetFormat
;(Note: Be wary of converting an integer to a float and back to an integer.
; An integer has 32 bits of data, whereas a float has only 27 bits of data.)
v = 1234
SetFormat, Float, 08.0 ; (08 for zero padded 8 digits total, .0 for zero decimal places)
v += 0.0               ; v converted to float, add zero, convert back to string
MsgBox v = %v%         ; v = '00001234'

v = 1234
SetFormat, Float, 8.0  ; (8 for space padded 8 digits & spaces total, .0 for zero decimal places)
v += 0.0               ; v converted to float, add zero, convert back to string
MsgBox v = %v%         ; v = '    1234'



/******************************************************************************
M:  working with FILE NAMES
;Set/Show Working Directory
SetWorkingDir,%A_ScriptDir%
MsgBox A_WorkingDir=%A_WorkingDir%

;Creating a File  (note: directory must exist)
FileAppend, test 10, MyFile10.log           ;<WorkingDir>\MyFile10.log
FileAppend, test 11, \MyFile11.log          ;C:\MyFile11.log
FileAppend, test 12, SubDir\MyFile12.log    ;<WorkingDir>\SubDir\MyFile12.log
FileAppend, test 13, SubDir\\\\\\\\\\\\\MyFile13.log   ;<WorkingDir>\SubDir\MyFile13.log Doesn't seem to matter how many extra \
V := "C:\TEMP"
FileAppend, test 14, %V%MyFile14.log        ;C:\TEMPMyFile14.log
FileAppend, test 15, %V%\MyFile15.log       ;C:\TEMP\MyFile15.log
FileAppend, test 16, %V%\\\\\\\\\\\MyFile16.log   ;C:\TEMP\MyFile16.log  Doesn't seem to matter how many extra \
FileAppend, test 17, ..\MyFile17.log        ;Up one directory from WorkingDir. <WorkingDir-^>\MyFile17.log
MsgBox ErrorLevel=%ErrorLevel%              ;FileAppend test for error. 0=SUCCESS, 1=FAIL



/******************************************************************************
N:  REGULAR EXPRESSIONS
(Note: AutoHotkey uses PCRE Perl-compatible format)

N1:  Regular Expression RESOURCES

CHEAT SHEETS
Regular Expressions (RegEx) - Quick Reference: http://www.autohotkey.com/docs/misc/RegEx-QuickRef.htm
Regular Expression Cheat Sheet: http://regexlib.com/CheatSheet.aspx
One Page Reference Cheat Sheet: http://www.regular-expressions.info/reference.html
Replacement Text Reference: http://www.regular-expressions.info/refreplace.html

HEAVY DOCUMENTATION
Syntax of regular expressions in Perl: http://search.cpan.org/dist/perl/pod/perlre.pod
Syntax of regular expressions in Perl: http://perldoc.perl.org/perlre.html
Concatenation of the PCRE man pages: http://www.pcre.org/pcre.txt
Perl Compatible Regular Expressions: http://en.wikipedia.org/wiki/PCRE

PROGRAMS
RegExBuddy: http://www.regexbuddy.com ($40) Screenshot: http://www.regexbuddy.com/screen.html

LIBRARIES
Regular Expression Library: http://regexlib.com/
Categories: http://www.regular-expressions.info/examples.html A Collection/Library Of Regular Expressions: http://www.autohotkey.com/forum/viewtopic.php?t=13544
N2:   Regular Expression EXAMPLES

Examples from: http://www.regular-expressions.info/numericranges.html
Matching Floating Point Numbers with a Regular Expression
Here are a few more common ranges that you may want to match:
000..255:       ——  ^([01][0-9][0-9]|2[0-4][0-9]|25[0-5])$
0 or 000..255:  ——  ^([01]?[0-9]?[0-9]|2[0-4][0-9]|25[0-5])$
0 or 000..127:  ——  ^(0?[0-9]?[0-9]|1[0-1][0-9]|12[0-7])$
0..999:         ——  ^([0-9]|[1-9][0-9]|[1-9][0-9][0-9])$
000..999:       ——  ^[0-9]{3}$
0 or 000..999:  ——  ^[0-9]{1,3}$
1..999:         ——  ^([1-9]|[1-9][0-9]|[1-9][0-9][0-9])$
001..999:       ——  ^(00[1-9]|0[1-9][0-9]|[1-9][0-9][0-9])$
1 or 001..999:  ——  ^(0{0,2}[1-9]|0?[1-9][0-9]|[1-9][0-9][0-9])$
0 or 00..59:    ——  ^[0-5]?[0-9]$
0 or 000..366:  ——  ^(0?[0-9]?[0-9]|[1-2][0-9][0-9]|3[0-6][0-9]|36[0-6])$
Examples from: http://www.codeproject.com/KB/dotnet/regextutorial.aspx
    1. elvis                 Find elvis
    2. \belvis\b             Find elvis as a whole word
    3. \belvis\b.*\balive\b  Find text with "elvis" followed by "alive"
    4. \b\d\d\d-\d\d\d\d     Find seven-digit phone number
    5. \b\d{3}-\d{4}         Find seven-digit phone number a better way
    6. \ba\w*\b              Find words that start with the letter a
    7. \d+                   Find repeated strings of digits
    8. \b\w{6}\b             Find six letter words
    9. .^\d{3}-\d{4}$        Validate a seven-digit phone number
   10. \b\w{5,6}\b           Find all five and six letter words
   11. \b\d{3}\s\d{3}-\d{4}  Find ten digit phone numbers
   12. \d{3}-\d{2}-\d{4}     Social security number
   13. ^\w*                  The first word in the line or in the text
   14. \(?\d{3}[) ]\s?\d{3}[- ]\d{4}  A ten digit phone number
   15. \S+                   All strings that do not contain whitespace characters
   16. \b\d{5}-\d{4}\b|\b\d{5}\b           Five and nine digit Zip Codes
   17. (\(\d{3}\)|\d{3})\s?\d{3}[- ]\d{4}  Ten digit phone numbers, a better way.
                                           This expression will find phone numbers in several formats, like
                                           "(800) 325-3535" or "650 555 1212".
                                           The "\(?" searches for zero or one left parentheses,
                                           "[) ]" searches for a right parenthesis or a space. The
                                           "\s?" searches for zero or one whitespace characters.
                                           Unfortunately, it will also find cases like
                                           "650) 555-1212" in which the parenthesis is not balanced.
                                           Below, you'll see how to use alternatives to eliminate this problem.
   18. (\d{1,3}\.){3}\d{1,3}               A simple IP address finder
   19. ((2[0-4]\d|25[0-5]|[01]?\d\d?)\.){3}(2[0-4]\d|25[0-5]|[01]?\d\d?)  IP finder
   20. \b(\w+)\b\s*\1\b      Find repeated words
   21. \b(?<Word>\w+)\b\s*\k<Word>\b   Capture repeated word in a named group
   22. \b\w+(?=ing\b)        The beginning of words ending with "ing"
   23. (?<=\bre)\w+\b        The end of words starting with "re"
   24. (?<=\d)\d{3}\b        Three digits at the end of a word, preceded by a digit
   25. (?<=\s)\w+(?=\s)      Alphanumeric strings bounded by whitespace
   26. \b\w*q[^u]\w*\b       Words with "q" followed by NOT "u"
   27. \b\w*q(?!u)\w*\b      Search for words with "q" not followed by "u"
   28. \d{3}(?!\d)           Three digits not followed by another digit
   29. (?<![a-z ])\w{7}      Strings of 7 alphanumerics not preceded by a letter or space
   30. (?<=<(\w+)>).*(?=<\/\1>)  Text between HTML tags
   31. Text between HTML tags (see referenced source page above)
   32. a.*b                  The longest string starting with a and ending with b
   33. a.*?b                 The shortest string starting with a and ending with b
Phone numbers:
    a. \(\d\d\d\)\s\d\d\d-\d\d\d\d
    b. \(\d{3}\)\s\d{3}-\d{4}
    4. \b\d\d\d-\d\d\d\d     Find seven-digit phone number
    5. \b\d{3}-\d{4}         Find seven-digit phone number a better way
    9. .^\d{3}-\d{4}$        Validate a seven-digit phone number
   11. \b\d{3}\s\d{3}-\d{4}  Find ten digit phone numbers
   14. \(?\d{3}[) ]\s?\d{3}[- ]\d{4}  A ten digit phone number
   17. (\(\d{3}\)|\d{3})\s?\d{3}[- ]\d{4}  Ten digit phone numbers, a better way.
Dates:
    a. (\d\d)-(\d\d)-(\d\d\d\d)    MM-DD-YYYY   (MM -& $1, DD -& $2, YYY -& $3)
    b. (\d\d\d\d)-(\d\d)-(\d\d)    YYYY-MM-DD   (YYYY -& $1, MM -& $2, DD -& $3)
    c. ^\d{1,2}\/\d{1,2}\/\d{4}$   XX/XX/YYYY where XX can be 1 or 2 digits long and YYYY is always 4 digits long.


/******************************************************************************
N3:  RegExReplace
N3.1: Basic examples
; Examples
f1 := RegExReplace("55555", "5", "five") ;f1 = "fivefivefivefivefive"
MsgBox f1=%f1%

f2 := RegExReplace("55555", "55", "x") ;f2 = "xx5"
MsgBox f2=%f2%

N3.2: EXTRACT Month, Day, Year, from 1/22/2009
;Regular Expression to EXTRACT Month, Day, Year, from 1/22/2009
;month & day can be 1 or 2 digits
 c := "xxxxxxxx 1/22/2009 yyyyyyyyyyyy"
 month := RegExReplace(c,".*?(\d{1,2})\/(\d{1,2})\/(\d{4})(.*)","$1")
 day   := RegExReplace(c,".*?(\d{1,2})\/(\d{1,2})\/(\d{4})(.*)","$2")
 year  := RegExReplace(c,".*?(\d{1,2})\/(\d{1,2})\/(\d{4})(.*)","$3")
 MsgBox month=%month%`nday=%day%`nyear=%year%

N3.3: An example of how we can step by step build up our Regular Expression
;An example of how we can step by step build up our Regular Expression
;Given string c, extract the data...
c := "  02-17-2009     238  Payment by Check.     314.15   9,265.35  "

;Trim leading and trailing spaces
c = %c%

; 1.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Start with "(.*)" which grabs the whole string
f3 := RegExReplace(c, "(.*)", "$1")
MsgBox f3=%f3%
; f3 = "02-17-2009     238  Payment by Check.     314.15   9,265.35"

; 2.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add "(\d\d)" to parse off the first two digits (the month)
f4 := RegExReplace(c, "(\d\d)(.*)", "{$1} {$2}")
MsgBox f4=%f4%
; f4 = "{02} {-17-2009     238  Payment by Check.     314.15   9,265.35}"

; 3.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add "-" to parse off the dash
f5 := RegExReplace(c, "(\d\d)-(.*)", "{$1} {$2}")
MsgBox f5=%f5%
; f5 = "{02} {17-2009     238  Payment by Check.     314.15   9,265.35}"

; 4.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add "(\d\d)" to parse off the second two digits (the day) and save it as $2
f6 := RegExReplace(c, "(\d\d)-(\d\d)(.*)", "{$1} {$2} {$3}")
MsgBox f6=%f6%
; f6 = "{02} {17} {-2009     238  Payment by Check.     314.15   9,265.35}"

; 5.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add "-" to parse off the dash
f6 := RegExReplace(c, "(\d\d)-(\d\d)(.*)", "{$1} {$2} {$3}")
MsgBox f6=%f6%
; f6 = "{02} {17} {-2009     238  Payment by Check.     314.15   9,265.35}"

; 6.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add "(\d\d\d\d)" to parse off the year (4 digits) and save it as $3
f7 := RegExReplace(c, "(\d\d)-(\d\d)-(\d\d\d\d)(.*)", "{$1} {$2} {$3} {$4}")
MsgBox f7=%f7%
; f7 = "{02} {17} {2009} {     238  Payment by Check.     314.15   9,265.35}"

; 7.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add " +" to parse off one or more spaces
f8 := RegExReplace(c, "(\d\d)-(\d\d)-(\d\d\d\d) +(.*)", "{$1} {$2} {$3} {$4}")
MsgBox f8=%f8%
; f8 = "{02} {17} {2009} {238  Payment by Check.     314.15   9,265.35}"

; 8.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add "(\d+)" to parse off the check number (one or more digits) and save it as $4
f9 := RegExReplace(c, "(\d\d)-(\d\d)-(\d\d\d\d) +(\d+)(.*)", "{$1} {$2} {$3} {$4} {$5}")
MsgBox f9=%f9%
; f9 = "{02} {17} {2009} {238} {  Payment by Check.     314.15   9,265.35}"

; 9.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add " +" to parse off one or more spaces
f10 := RegExReplace(c, "(\d\d)-(\d\d)-(\d\d\d\d) +(\d+) +(.*)", "{$1} {$2} {$3} {$4} {$5}")
MsgBox f10=%f10%
;f10 = "{02} {17} {2009} {238} {Payment by Check.     314.15   9,265.35}"

; 10.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add "(.*?)" to parse off the text (minimal match), followed by " {5}" to parse off 5 spaces
; (there apparently is always 5 spaces. This tells us when we're done parsing off the text.)
f11 := RegExReplace(c, "(\d\d)-(\d\d)-(\d\d\d\d) +(\d+) +(.*?) {5}(.*)", "{$1} {$2} {$3} {$4} {$5} {$6}")
MsgBox f11=%f11%
; f11 = "{02} {17} {2009} {238} {Payment by Check.} {314.15   9,265.35}"

; 11.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add "([\d,.]+)" to parse off the dollars and cents (one or more digits with possible commas and decimal point, e.g. 27,182.81)
f12 := RegExReplace(c, "(\d\d)-(\d\d)-(\d\d\d\d) +(\d+) +(.*?) {5}([\d,.]+)(.*)", "{$1} {$2} {$3} {$4} {$5} {$6} {$7}")
MsgBox f12=%f12%
; f12 = "{02} {17} {2009} {238} {Payment by Check.} {314.15} {   9,265.35}"

; 12.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add " {3}" to parse off 3 spaces (apparently always 3)
f13 := RegExReplace(c, "(\d\d)-(\d\d)-(\d\d\d\d) +(\d+) +(.*?) {5}([\d,.]+) {3}(.*)", "{$1} {$2} {$3} {$4} {$5} {$6} {$7}")
MsgBox f13=%f13%  ;f13 = "{02} {17} {2009} {238} {Payment by Check.} {314.15} {9,265.35}"

; 13.
; c := "02-17-2009     238  Payment by Check.     314.15   9,265.35"
; Add "([\d,.]+" to parse off the dollars and cents (one or more digits with possible commas and decimal point, e.g. 27,182.81)
f14 := RegExReplace(c, "(\d\d)-(\d\d)-(\d\d\d\d) +(\d+) +(.*?) {5}([\d,.]+) {3}([\d,.]+)(.*)", "{$1} {$2} {$3} {$4} {$5} {$6} {$7} {$8}")
MsgBox f14=%f14%
; f14 = "{02} {17} {2009} {238} {Payment by Check.} {314.15} {9,265.35} {}"
;        (the last empty {} indicates there's nothing left over)

N3.4: Find the $ dollar sign. Extract price and add a $.
;find the $ dollar sign
c := "xxx $17.25 yyy"
dollar := RegExReplace(c,"(.*?)(\$)(.*)","$2")
MsgBox dollar=%dollar%

;extract price and add a dollar sign
c := "xxx 17.25 yyy"
price := RegExReplace(c,"(.*?)([\d,.]+)(.*)","$$$2")
msgbox price=%price%   ; price = "$17.25"

; For RegExReplace replace string only:
;    To specify a literal $, use $$
;    $ is the only character that needs such special treatment in a RegEx replace string.
;    Backslashes are never needed to escape anything else in a RegEx replace string.
; (RegEx search string still needs to have many characters escaped.)



/******************************************************************************
O:  Misc AutoHotkey Notes & Debugging Tips

O1: Notes / Caveats

  • NOTE: 
ALL VARIABLES ARE STORED AS CHARACTER STRINGS !!!
Strings containing numbers are converted to numbers when needed, and the result is converted back to a string.
/******************************************************************************
  • NOTE: 
Closing */ must be first thing on line. Otherwise you'll be asking yourself, "Why does my script stop running at this point, as if the whole rest of the script was commented out?"

MsgBox Hello
/* here is a comment
and another comment */
MsgBox Goodbye    ;You'll never see this message
MsgBox Hello
/* here is a comment
and another comment
*/
MsgBox Goodbye    ;Now you're OK
/******************************************************************************
  • NOTE: 
      Space here ruins function call
      ↓
MyFunc (Param1)
MyFunc(Param1)

O2: Sending Debug Data To A Log File
;Example 1. Log a message
SetWorkingDir, %A_ScriptDir%  ;Set default directory to where this script file is located
LogFile := "MyLog.txt"
FileAppend, This is a message`n, %LogFile%  ;(note the trailing (`n) to start a new line. This could instead be a leading (`n) if you want.
;Example 2. Include a time stamp
SetWorkingDir, %A_ScriptDir%  ;Set default directory to where this script file is located
LogFile := "MyLog.txt"
FormatTime, TimeString, , yyyy-MM-dd hh:mm:ss tt
FileAppend, `n%TimeString% : This is a message`n, %LogFile%
;Example 3. Put it all in a function named LogMsg
SetWorkingDir, %A_ScriptDir%  ;Set default directory to where this script file is located
LogFile := "MyLog.txt"
LogMsg("This is a message")   ;Note LogMsg adds a leading (`n) so each message starts on a new line
LogMsg("Variable X = " . X )  ;Concatenate using the dot .
ExitApp

;---------------------------
;And here is our function:
LogMsg( msg )
{
  global LogFile
  FormatTime, TimeString, , yyyy-MM-dd hh:mm:ss tt
  FileAppend, `n%TimeString% : %msg%, %LogFile%
}
Update: I've had cases where using FileAppend too frequently causes it to occasionally fail. An expected line in the log file just isn't there. You can check ErrorLevel, but there's no way to get further info on why it failed. Tech note: This may be because FileAppend closes the file every time. That can be a lot of opening/closing a file.


O3: Capturing a screen image during run using IrfanView
/******************************************************************************
Capturing a screen image during run using IrfanView (www.irfanview.com)
*/
RunWait "C:\Program Files\IrfanView\i_view32.exe" "/capture=1  /convert=C:\TEMP\MyImage.bmp"


/******************************************************************************
P:  Misc AutoHotkey Scripts:

P1: Misc AutoHotkey Scripts
P2: Index of notable scripts found in the AutoHotkey Forum : http://www.autohotkey.com/wiki/index.php?title=Script_Listing
  • 1 AutoHotkey Related
    • 1.1 Ports/custom builds
      • 1.1.1 Windows NT+
      • 1.1.2 Windows CE
      • 1.1.3 Windows/Linux/Mac (.NET/Mono)
    • 1.2 Compile AutoHotkey yourself
      • 1.2.1 MS Visual C++
      • 1.2.2 GCC
    • 1.3 Use AutoHotkey with other programming/scripting languages
      • 1.3.1 Any
    • 1.4 Use other programming/scripting languages inline in AutoHotkey
      • 1.4.1 Perl
      • 1.4.2 C#/VB
      • 1.4.3 VBScript/JScript, VB/VBA/MS Office
      • 1.4.4 Assembly/Machine code
      • 1.4.5 C/C++
      • 1.4.6 Lisp/ECL
    • 1.5 Scripts
    • 1.6 Tools
    • 1.7 Editors
  • 2 GUI
    • 2.1 General
    • 2.2 All
    • 2.3 3P Controls
    • 2.4 MsgBox
    • 2.5 ListBox
    • 2.6 Splash
    • 2.7 Menu
    • 2.8 Templates
    • 2.9 Hotkey
    • 2.10 Button
    • 2.11 Hyperlink
    • 2.12 ListView
    • 2.13 Edit
    • 2.14 Other
    • 2.15 Tooltip
    • 2.16 TreeView
  • 3 Functions
  • 4 Audio and Video
  • 5 File Management and Searching
  • 6 File Reading & Parsing
  • 7 Internet related
  • 8 XML, HTML and BBCode
  • 9 Window Manipulation
  • 10 Keyboard Enhancements
  • 11 Mouse Related
  • 12 Clipboard Manipulation
  • 13 Games
    • 13.1 Game Related
  • 14 Fun
  • 15 Images
  • 16 Time and Scheduling
  • 17 Encryption / Encoding / Binary
  • 18 System Related
  • 19 Security
  • 20 Miscellaneous


P3: AHK Functions - ()
http://www.autohotkey.com/forum/viewtopic.php?t=8728

P4: Library for Text File Manipulation : http://www.autohotkey.net/~heresy/Functions/TXT.ahk


P5: Tray Icons : http://www.autohotkey.com/wiki/index.php?title=Script_Listing


P6: Force Exit another AutoHotkey script
To force Exit another AutoHotkey script (and have it's icon removed from the system tray):
WM_COMMAND = 0x111
ID_FILE_EXIT = 65405
PostMessage, WM_COMMAND, ID_FILE_EXIT, 0, , <window-title>
Example: To end the DimScreen program (an AutoHotkey script at http://www.donationcoder.com/Software/Skrommel/#DimScreen)
WM_COMMAND = 0x111
ID_FILE_EXIT = 65405
PostMessage, WM_COMMAND, ID_FILE_EXIT, 0, , DimScreen Screen
Notes: The above only works for AutoHotkey scrips (*.ahk, or compiled to *.exe)
Notes: To determine the Window Title, run Process Explorer
Notes: AutoHotkey has the following WM_COMMAND numbers defined in resource.h
ID_FILE_PAUSE65403
ID_FILE_SUSPEND65404
ID_FILE_EXIT65405
(0x111 is WM_COMMAND)

Tech note: Other WM_COMMAND numbers defined in AutoHotkey source file resource.h (I haven't tried any of these to see what they do)
ID_FILE_RELOADSCRIPT65400
ID_FILE_EDITSCRIPT65401
ID_FILE_WINDOWSPY65402
ID_FILE_PAUSE65403
ID_FILE_SUSPEND65404
ID_FILE_EXIT65405
ID_VIEW_LINES65406
ID_VIEW_VARIABLES65407
ID_VIEW_HOTKEYS65408
ID_VIEW_KEYHISTORY65409
ID_VIEW_REFRESH65410
ID_HELP_USERMANUAL65411
ID_HELP_WEBSITE65412

Another way to identify the AutoHotkey script you want to Exit(/Suspend/Pause):
WM_COMMAND = 0x111
ID_FILE_EXIT = 65405
DetectHiddenWindows, On

WinGet, AList, List, ahk_class AutoHotkey       ; Make a list of all running AutoHotkey programs
Loop %AList% {                                  ; Loop through the list
  ID := AList%A_Index%
  WinGetTitle, ATitle, ahk_id %ID%              ; (You'll notice this isn't the same 'window title')
  MsgBox, 3, %A_ScriptName%, %ATitle%`n`nEnd?
  IfMsgBox Cancel
    Break
  IfMsgBox Yes
    PostMessage,WM_COMMAND,ID_FILE_EXIT,0,,% "ahk_id" AList%A_Index%   ; End the process (65404 to suspend, 65403 to pause)
}
ExitApp


/******************************************************************************
Q:  NAVIGATING WEB SITES
See example file WebsiteNav.ahk

Q1:  DETERMINING WHEN A WEBPAGE HAS FINISHED LOADING
See FAQ: http://www.autohotkey.com/docs/FAQ.htm#load

Q2:  POSITION US ON A CERTAIN CONTROL
Examples are from simple to more complex. All examples here are demonstrated in file WebsiteNav.ahk


Q3: SEARCH FOR A COLORED PIXEL
Note: If I'm searching a white background for black text, I find it works better to search for "not white" rather than search for "black", because sometimes that black text isn't really black when you look at it closely.

The following actually goes quite fast if you comment out the moving of the mouse. I move the mouse here for demonstration purposes.
WinGetPos, winposX, winposY, Width, Height, A  ;Get window Width, Height
;MsgBox, 0, , winposX=%winposX%`n winposY=%winposY% `nWidth=%Width% `nHeight=%Height%,

;Calculate a starting position
X := Width - 60
Y := Height / 2
MouseMove, X, Y, 7

MsgBox, 0, , Move left until we find "not white", 1.2

;move left until we find "not white"
loop 200
{
    MouseMove, X, Y, 0
    PixelGetColor, color, X, Y, RGB
    ;MsgBox, 0, , color=%color%, 0.1
    if (color <> "0xFFFFFF")
    {
      Goto FOUND_TCOLOR
    }
    X -= 1
}
;If we drop out here, it means we failed to find our target
MsgBox, 0, , Failed to find color "not white", 2
goto Exit

FOUND_TCOLOR:
MsgBox, 0, , Found "not white". color = %color%, 2

Exit:
MsgBox, 0, , The End, 2
ExitApp

/************************************************
R:  NEWBIE RECOMMENDED LEARNING SEQUENCE
Reference: Recommended by jaco0646 (thank you jaco0646)
http://www.autohotkey.com/forum/viewtopic.php?t=29204) Similarly:
Suggested order of study for AutoHotkey newbies:
First:
  1. read the Tutorial
  2. the Scripts page
  3. the FAQ

Afterwards, recommend learning concepts in the following order:
  1. Hotstrings
  2. Hotkeys
  3. Mouse Clicks & Mouse HotKeys
  4. Variables
  5. Loops - especially Parsing Loops
  6. String commands - (e.g. StringMid, StringReplace)
  7. If,Else statements
  8. Expressions
  9. Arrays & Dynamic variables - (StringSplit)
  10. GoSub & Functions
  11. GUIs
  12. Windows Messages
  13. DllCall


/******************************************************************************
S:  PRESS ESC TO CANCEL THIS SCRIPT
Defining Hotkeys
A hotkey definition line stops execution at that point, so if you want the
script to run to the end but have the ESC key available to terminate the script,
put the hotkey definition at the end, just after your ExitApp statement.
;Press ESC to cancel this script
Esc::ExitApp

/******************************************************************************
T:  THE AUTOHOTKEY RUN COMMAND

Program:
Run, ShowParams.exe  hello  goodbye  Friday
AutoHotkey script:
Run, autohotkey.exe  ShowParams.ahk  hello  goodbye  Friday
VBScript:
Run, cscript.exe  ShowParams.vbs  hello  goodbye  Friday
JScript:
Run, cscript.exe  ShowParams.js  hello  goodbye  Friday
Any command:
                    ┌───── cmd.exe strips off these outer " ───────┐
Run, "%comspec%" /c ""ShowParams.ahk"  "hello"  "goodbye"  "friday"", , Hide
Hide is specified to prevent the Command Prompt Window from popping up.
/c causes Command Prompt Window to exit after command is executed.
/k instead of /c would cause Command Prompt Window to remain open after command is executed. Useful for debugging.


Notes:
AutoHotkey scripts:
Why does specifying just 'autohotkey.exe' work? Because the AutoHotkey installer adds the following entry to the registry:
[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\AutoHotkey.exe]
@="C:\\Program Files\\AutoHotkey\\AutoHotkey.exe"

VBscript and JScript:
You may also use wscript.exe — wscript.exe is the windows version, cscript.exe is the console version. You'll find them in the System32 directory.
(JScript is Microsoft's own version of JavaScript.)

The comspec environment variable usually equates to C:\Windows\System\System32\cmd.exe . On Windows 95,98,ME it equates to COMMAND.COM . It's also possible the user may have changed it to run a fancier command prompt such as JPSoft's Take Command command line utility (http://jpsoft.com)

The AutoHotkey RUN command currently does not parse <target> the way you'd expect it to, so the results often aren't quite what you wanted. Here's how it works:
  1. Autohotkey parses off the <target> parameter.
    The <target> parameter is delimited by a comma, so if you want to include a comma somewhere in the target parameter, you need to escape it with a `
  2. Autohotkey expands any variables (e.g. %day%).
    Variables are delimited by %, so if you want to include a literal % somewhere in the <target> parameter, you need to escape it with a `
  3. AutoHotkey tries calling CreateProcess() passing the processed <target> parameter as the lpCommandLine argument.
  4. If CreateProcess() fails, AutoHotkey tries calling ShellExecute() passing the processed <target> parameter as the lpFile parameter. Note: This is where it would be nice if AutoHotkey would split <target> between the command and parameters, passing the command as lpFile and the parameters as lpParameters, but it doesn't. It instead passes the entire line as the lpFile parameter, leaving the lpParameters argument NULL. The reason for this is the design decision mentioned in the AutoHotkey source code file script.cpp routine ActionExec: "User can launch a document name containing spaces without having to enclose it in double quotes."

An alternative to using Run is to directly call ShellExecute() :
command = ShowParams.ahk
params = hello goodbye Friday
res := DllCall("shell32\ShellExecuteA"
      , "UInt", 0             ; hwnd
      , "UInt", 0             ; lpOperation
      , "Str", command        ; lpFile
      , "Str", params         ; lpParameters
      , "Str", A_WorkingDir   ; lpDirectory
      , "UInt", 0)            ; nShowCmd
MsgBox (%ErrorLevel%) %res%

/******************************************************************************
U:  PASSING PARAMETERS TO AUTOHOTKEY SCRIPTS
On Windows, parameters are parsed off the command line after the new process is created, by the new process. It's considered the responsibility of the newly started application to call the GetCommandLine() API to retrieve the command line string and parse it.

How does a C/C++ program on Windows get argv[]? The C/C++ compiler which compiles the program secretly adds extra code to the executable that retrieves and parses the command line to extract the parameters before calling WinMain (or main). Thus, for a C/C++ executable on Windows, the parameter parsing rules are determined by the C/C++ compiler that compiled the program.

AutoHotkey is written in C++ and obtains its parameters via the argv[] vector.1 Thus it uses the Microsoft C/C++ Parameter Parsing Rules. The rules are:

  1. Parameters are always separated by a space or tab (multiple spaces/tabs OK)
  2. If the parameter does not contain any spaces, tabs, or double quotes, then all the characters in the parameter are accepted as is (there is no need to enclose the parameter in double quotes).
  3. Enclose spaces and tabs in a double quoted part
  4. A double quoted part can be anywhere within a parameter
  5. 2n backslashes followed by a " produce n backslashes and start or end a double quoted part
  6. 2n+1 backslashes followed by a " produce n backslashes + a literal quotation mark
  7. n backslashes not followed by a quotation mark produce n backslashes
  8. If a closing " is followed immediately by another ", the 2nd " is accepted literally and added to the parameter (this is the undocumented rule)
For more on passing parameters to programs, with numerous examples, see the essay How Command Line Parameters Are Parsed


Notes:
1. Actually AutoHotkey uses the __argv[] vector.

/******************************************************************************
V:  PASSING PARAMETERS TO ANY PROGRAM
You aren't sure how to escape the special characters in that parameter so it comes out right? See the essay How Command Line Parameters Are Parsed


/******************************************************************************

My title: "" %% (), And All That, is taken from the wonderful book, Div, Grad, Curl, And All That: An Informal Text on Vector Calculus by H. M. Schey (1973)

History:
Version 1.00 02/28/2009
Version 1.04 03/08/2009
Version 1.05 03/09/2009
Version 1.09 03/26/2009
Version 1.10 04/30/2009
Version 1.12 05/15/2009
Version 1.14 05/24/2009
Version 1.19 06/01/2009
Version 1.21 08/24/2009
Version 1.22 01/02/2011