I don't want to set off a religious war. AHK and AutoIt3 have the same roots. I use both.
I find AHK superior in the area of Mouse Hotkeys. Also you can use the library functions without listing a bunch of include files.
I find AutoIt3 has better scoping. It's easier to create user libraries of general purpose routines to include in your scripts. Also AutoIt3 string handling is much simpler. Just double quote strings as in most programming languages.
Often I will code the main app in AutoIt3 and have a helper exe to do the Mouse Hotkey handling in AHK.
For alternatives the big dividing line other than to Window or not to Window is COM support. FreeBASIC is a free basic compiler that doesn't require run-times. It produces very small stand-alone 32 bit Windows applications. But the COM support, well, you might as well say there isn't any. It is easy to call WinAPI functions or other functions in DLLs though.
I guess I'm beating around the bush because there's no way to answer your question without knowing what you want to do.
Mouser is right that if you want platform interoperability then you are better off looking at languages such as Python, Perl, Java, Rexx flavors etc.. and for compiled languages C/C++.
If we are talking Windows only I would try AutoIt3 first. If you can do AHK the AutoIt3 code blocks are much easier to deal with. There's no "expression mode" where things act one way and non expression mode where stuff acts another way. It's just blocks, functions, loops, select and switch like most procedural languages. AutoIt3 has native support for objects. It doesn't have associative arrays but you can get one on XP or later just by using Scripting.Dictionary.
I wrote some wrapper functions to make Scripting.Dictionary easy to use in my AutoIt3 programs. The compare mode 1 is compare as strings with no case sensitivity as that's the most generally useful for me.
;use Scripting.Dictionary object for simple associative arrays
Func _AssocArray()
Local $aArray = ObjCreate("Scripting.Dictionary")
If @error Then
Return SetError(1, 0, 0)
EndIf
$aArray.CompareMode = 1
Return $aArray
EndFunc ;==>_AssocArray
Func _AssocArrayDestroy(ByRef $aArray)
If Not IsObj($aArray) Then
Return False
EndIf
$aArray.RemoveAll()
$aArray = 0
Return True
EndFunc ;==>_AssocArrayDestroy
Here's one I use frequently to get the hex color code when indexing the color list by the name of the color:
Func _ColorList()
Local $colorList = _AssocArray()
If @error Then
Return SetError(1, 0, 0)
EndIf
$colorList("AntiqueWhite") = 0xFAEBD7
$colorList("Black") = 0x000000
$colorList("Blue") = 0x0000FF
$colorList("Brown") = 0xA52A2A
$colorList("CadetBlue") = 0x5F9EA0
$colorList("Chocolate") = 0xD2691E
$colorList("Coral") = 0xFF7F50
$colorList("CornflowerBlue") = 0x6495ED
$colorList("DarkBlue") = 0x00008B
$colorList("DarkCyan") = 0x008B8B
$colorList("DodgerBlue") = 0x1E90FF
$colorList("ForestGreen") = 0x228B22
$colorList("Gold") = 0xFFD700
$colorList("Gray") = 0x808080
$colorList("Green") = 0x008000
$colorList("HotPink") = 0xFF69B4
$colorList("LightGreen") = 0x90EE90
$colorList("LightPink") = 0xFFB6C1
$colorList("LightSeaGreen") = 0x20B2AA
$colorList("Lime") = 0x00FF00
$colorList("Magenta") = 0xFF00FF
$colorList("Maroon") = 0xB03060
$colorList("MediumTurquoise") = 0x48D1CC
$colorList("MediumVioletRed") = 0xC71585
$colorList("MistyRose") = 0xFFE4E1
$colorList("Navy") = 0x000080
$colorList("Olive") = 0x808000
$colorList("Orchid") = 0xDA70D6
$colorList("PaleGreen") = 0x98FB98
$colorList("PaleVioletRed") = 0xDB7093
$colorList("Pink") = 0xFFC0CB
$colorList("Plum") = 0xDDA0DD
$colorList("Purple") = 0x800080
$colorList("Red") = 0xFF0000
$colorList("RoyalBlue") = 0x4169E1
$colorList("Sienna") = 0x00A0522D
$colorList("Silver") = 0xC0C0C0
$colorList("SkyBlue") = 0x87CEEB
$colorList("SteelBlue") = 0x004682B4
$colorList("Tan") = 0xD2B48C
$colorList("Teal") = 0x008080
$colorList("Violet") = 0xEE82EE
$colorList("Wheat") = 0xF5DEB3
$colorList("White") = 0xFFFFFF
$colorList("Yellow") = 0xFFFF00
Return $colorList
EndFunc ;==>_ColorList