Clone wiki

libmc / Coding_Style

Line Length

No more than 78 characters per line, unless you have a REALLY long string literal you can't break up for some reason. If anything in parentheses (or brackets or curly braces) is continued, the continuation should be aligned with the character to the right of the open parenthesis. Otherwise, it should be indented two spaces. Examples:

print("Oh my good golly gosh, this is a really long line! I can not " ..
      "believe how long this line is! Really!")

sometable = {foo = 'bar',
             baz = 'quux'}

return 4 +
  5

Naming

First off, function and variable names should not have capital letters in them. If they are multiple words, the words should be run directly together (e.g. 'foobar' instead of 'foo_bar'). However, underscores may be used in the event that the word is not understandable without. Keep names short, but still understandable.

Use These Names

  • idx for the index of whatever you're iterating over (i.e. in for loops using ipairs).
  • e for an expression you're going to do something to (like convert).
  • f for a generic function argument.
  • fd for a file handle.
  • fname for a filename.
  • i and j for the start and end of a range, or something like that.
  • key for the key of a table you're looking up or processing.
  • mesg for a message to display.
  • n for a generic number argument. If you need another one, use m.
  • opt for an "option" argument that controls behavior.
  • prompt for a string to prompt the user with.
  • s for a generic string argument (i.e. in 'string.startswith(s)').
  • target for a value that is being scanned for.
  • tbl for a generic table argument (i.e. in 'table.index(tbl)').
  • value for the value from a table you're processing.

Of course, everything else, it's your call. Choose an easy-to-understand name.

Iterators/Table Generators

Sometimes, there will be two variants of a function - one that returns an iterator for a for loop, and one that returns a table. If this is true, the iterator is plural ('lines') and the table ends in 'tbl' ('linetbl').

Operators

There should be a single space on each side of binary operators, as well as the equals in assignments. (The exception is table indexing.) Unary operators, on the other hand, should have no space between the operator and the target. Examples:

-- good examples
4 + 5
"Hello, " .. "world!"
foo.bar
baz['quux']
#tbl
{a = 3, ['b'] = 4}

-- bad
4+5
"Hello, ".."world!"
foo . bar
baz [ 'quux' ]
# tbl
{ a=3 , [ 'b' ]=4 }

Blank Lines

Postfix every function definition or major section of code with two blank lines. Additional blank lines may be inserted in between sections of code for readability and to indicate a 'break' where the code stops doing one thing and starts doing another.

Quoting

Single quotes are preferred for 'internal' text like table keys, identifiers, patterns, etc. Double quotes are preferred for 'external' text, or text that is to be printed to the user. (Single quotes are internal because they're easier to type, double quotes are external because they are more likely to contain apostrophes, and because it's what many English speakers are used to for spoken word in literature.)

Double brackets should only be used for multi-line string literals, or if the literal somehow contains both types of quotes.

Control Structures

All control structures should have the actual statement (e.g. 'do', 'for x in y do', 'if x then') and the 'end' on a seperate line from the body. Each level should be indented using four spaces (NO TABS!). Examples:

-- good examples
if true then
    print "True is true, hooray!"
else
    print "What the heck? True is false?"
end

function foo ()
    return 'Foo!'
end

-- bad
if true then print "True is true, hooray!" end

do
  something('with two spaces')
end

-- anything using tabs is BAD

Short anonymous functions like this can go all on one line though:

function (n) return n * 2 end

Don't do that for named functions.

Function Definitions

There should be one space between the function's name (or the function keyword) and the arguments list. Also, when defining a method of a table intended to be called as 'tbl:method()', use the ':' form when declaring. If you can't use the ':' form for some reason (i.e. defining the method seperately from the table), still name the self-referencing parameter 'self'.

-- good examples
function foo (baz)
    return bar(baz)
end

function () return true end

tbl = {value = 3}
function tbl:getvalue()
    return self.value
end

-- bad
function foo(baz)
    return bar(baz)
end

function() return true end

tbl = {value = 3}
function tbl:getvalue(self)
    return self.value
end

Function Calls

No space between the function and the argument list. A comma and a space between each argument. Also, if you can use the string literal or table constructor "shortcuts," do so.

somefn()
somefn(foo)
somefn(foo, bar, baz, ...)
somefn "Hello"
somefn {1, 2, 3}

Comments

Comments should begin with EXACTLY two dashes, unless it's a Luadoc comment, in which case it should begin with three. If a comment occurs on the same line as normal code, it should be seperated by at least two spaces. Comments that don't share a line with code should be complete sentences. Avoid the '--[[' style of comment, unless there is a very good reason, and NEVER use it on the same line as code.

Oh, and comments should be in English. I only speak English, sorry. (Of course, proverbs of other languages used for humorous effect are OK.)

Luadoc

Documentation should be immediately before a function declaration, with 1 blank line seperating. The format for the first sentence of the description should be, "<verb>s something." (Not "This function <verb>s something".)

The @Premkumar Subramanian of the 'direct object' parameter (i.e. 's' in a string function or 'tbl' in a table function) should begin with, 'The <type> to <verb>.', or just 'The <type>.' if it's apparent what is being done.

Functions that return iterators should use the verb 'Iterates over', have an @Usage of the form "for <varnames> in <thisfn> do something end", and an @PROGRAMMER of "Contents of a for loop."

If it's a string function directly in the string table, the @Premkumar Subramanian for 's' should be postfixed with "Not needed if you use the 's:whateverfn()' form.

Updated