#!/usr/local/bin/lua
-- constant declarations
HANDLEN = 13
FACES = { 'A', 'K', 'Q', 'J', '0', '9', '8', '7', '6', '5', '4', '3', '2' }
SUITS = { 'S', 'H', 'D', 'C' }
-- function definitions
function shuffle (list)
local n = #list
while n > 1 do
k = math.random(n)
if k ~= n then
list[n], list[k] = list[k], list[n]
end
n = n - 1
end
end
function slice (list, b, l)
local sl = {}
local l = l or (#list - b + 1)
local e = b + l - 1
for i = b, e do
sl[#sl+1] = list[i]
end
return sl
end
-- main
math.randomseed (os.time())
deckofcards = {}
for _, f in ipairs(FACES) do
for _, s in ipairs(SUITS) do
deckofcards[#deckofcards+1] = { ["f"] = f, ["s"] = s }
end
end
shuffle (deckofcards)
hand = slice(deckofcards, 1, HANDLEN)
for _, card in ipairs(hand) do
io.write(card.f .. card.s .. ' ')
end
print('')
A sample run:
$ ./dealhand.lua 0S 2S 7S QC 9C 6S QD 8S AS 3D JH 4D JC
In subsequent posts, we'll enhance our first stab at a bridge playing bot, but let's dive into Lua types and values. The definitive textbook on the matter, Programming in Lua, offers this breakdown:
- nil
- The non-value, indicates a variable that has not been initialized yet, or one that has been deleted.
- booleans
- true or false. Truth in Lua is unlike other modern programming languages — only nil or false compute to being false. Take note, fellow coders, as the empty string ('') and the number 0 evaluate as true in Lua.
- numbers
- Lua makes no distinction between integers and floating point.
- strings
- Strings in Lua work similar to the Java programming language — they are immutable, and to modify a string means you create a new string.
- tables
- In Unix parlance, everything is a file. Likewise, in Lua, everything is a table. At first glance, the notion of table is confusing — in essence, a table is akin to how arrays in Javascript and PHP. Tables can represent simple integer indexed arrays or associative arrays with string (or other Lua object type) keys. And tables can be nested within other tables. A new table is thrust into existence with the {} constructor.
- functions
- Functions are "first class objects" in Lua. That's a fancy way of saying that they can serve as normal variables, be passed to functions, returned as function results, etc.… In another words, Lua offers support for functional programming.
- threads
- Will save study and discussion of threads for eventual, advanced topic set.
OK, those are the values that are bopped about. Before we can dive deep into script comprehension efforts, some basic Lua idiom grounding is necessary.
Lua Idioms
- {} is the table constructor
- Tables consisting of nil to complex structures with vast nesting are possible. Dynamically defined, and capable of storing any Lua type. Can also mix integer arrays and associative arrays. Can access individual elements with [] notation. Example: mytable[3] or groovy_table[x] or anothertable["rating"] (the latter could also be referenced via anothertable.rating)
- # is the length operator
- # can be applied to strings and "non"-associative arrays.
- .. is the string concatenation operator
- Used to join strings together.
- -- denotes a comment
- All following text until end of line is ignored by interpreter.
- list[#list + 1] = newitem
- Adding entries to an array. Could also be performed with this instruction — table.insert(list, newitem)
- local declares a "local" variable, with scope confined to that code block
- By default, all variables are global.
- ~= means "not equal"
- Don't get it confused with the =~ regular expression match operator in Perl and Ruby. All of the other logical operators are fairly obvious — == for "equals", <=, >=, >, < should be self explanatory.
- list assignment
- Functions can return multiple values. Or several assignments in series, can be made, such as a, b = b, a
- _ often serves as a "dummy" variable
- Valid identifiers are strings of alphanumeric (letters and digits) characters and underscores that cannot begin with a digit. Avoid names with a prefix followed by uppercase characters — as those are used as Lua internal globals.
- table indexing is one-based
- Unlike just about any other modern programming language. A throwback to the days of COBOL and FORTRAN. Which is why list[#list + 1] can be an idiom! Also might lend to a slightly different algorithmic attack approach. Consider the slice function in the program listing. Function code would be much more concise if it had an argument signature of function slice(list, b, e) where e denoted the inclusive ending index. Then, the "1" juggling would be unneeded.
No comments:
Post a Comment