Difference between revisions of "Anri-chan/Source/Coding Standards/Perl"
From SDA Knowledge Base
(New page: NOTE: we haven't yet made the final decision for what anri 4 will be coded in. these guidelines are only for reference and may have no meaning if we decide to go with a language other than...) |
(new header and info about commenting subroutines) |
||
Line 5: | Line 5: | ||
#!/usr/bin/perl | #!/usr/bin/perl | ||
use warnings; | use warnings; | ||
− | use strict; | + | use strict 'subs'; |
+ | package anri; | ||
</nowiki></pre> | </nowiki></pre> | ||
Line 25: | Line 26: | ||
=Comments= | =Comments= | ||
− | Immediately before the described functionality. Do not mix code and comments unless this is a regex-to-English translation block (see below). | + | Immediately before the described functionality. Do not mix code and comments unless this is a regex-to-English translation block (see below). Also, comment subroutines before the subroutine declaration, not before calls to it. |
<pre><nowiki> | <pre><nowiki> |
Revision as of 14:55, 22 August 2008
NOTE: we haven't yet made the final decision for what anri 4 will be coded in. these guidelines are only for reference and may have no meaning if we decide to go with a language other than perl.
Contents
Headers
#!/usr/bin/perl use warnings; use strict 'subs'; package anri;
Whitespace and blocks
Use tabs (rather than spaces) for indentation. Mediawiki supports them, as do the major text editors. 8 spaces per tab.
Blocks example:
for (<*.ac3>) { if (m/^([^ ]+) .+DELAY (-?[0-9]+)ms/) { $delay=($2/1000); } elsif (m/^([^.]+)\.ac3$/) { $delay=0; } print "ac3source(MPEG2source(\"$1.d2v\",upconv=1),\"$_\").delayaudio(".$delay.")\n"; }
Comments
Immediately before the described functionality. Do not mix code and comments unless this is a regex-to-English translation block (see below). Also, comment subroutines before the subroutine declaration, not before calls to it.
############################################################################ # Initialisation # # Some obvious stuff in here. Desktop location is set using the win32api # module under Windows and the Carbon API under Mac OS X. Linux users will # be prompted. ############################################################################ $anri_ver = 4; $dgmpgdec_dir = 'dgmpgdec150'; $vdub = 'virtualdub-1.7.6';
Variable scope
Anri is a small project and will never be distributed as a Perl module. Therefore, to simplify things, all variables have global scope. Never use "my" before a variable name for any reason.
Variables in strings
${variable}
Files and directories as variables
Always use single forward slash as the path delimiter. A directory variable should never end in /.
$afile = "sda.avs"; $adir = "c:/program files/anri"; $sdaavs = "${adir}/${afile}";
for versus foreach
Up to the discretion of the programmer. But if the scope of $_ is ever confusing (e.g. you have to use $_ inside a doubly-nested block), use foreach with a descriptive variable name.
Regex
Document all regex with example input and output strings. Also, use /x to add English comments where the pattern is particularly dense. The below pattern is not particularly dense, but it keeps things short for the sake of example. Note the tabs before the comments.
#Write the source declaration if we have AC3 audio with a delay. #input example: contra T01 2_0ch 256Kbps DELAY -64ms.ac3 #output example: ac3source(MPEG2source("contra.d2v",upconv=1),"contra T01 2_0ch 256Kbps DELAY -64ms.ac3").delayaudio(-0.064) / #start of pattern ^ #start of input ([^ ]+) #one or more character other than a space. this is our "basename" for the .d2v, going to be $1 [ ] #a space .+ #one or more of any character other than a newline DELAY #the literal word DELAY [ ] #a space (-?[0-9]+) #Maybe we have a negative sign, maybe we don't. Also one or more numbers. This is going to be $2, our delay value. ms #literal string for milliseconds in filename /x; #end of pattern with comment flag print "ac3source(MPEG2source(\"$1.d2v\",upconv=1),\"$_\").delayaudio(".($2/1000).")\n";
Some good info on regex in perl is available at perl.org.
Passing arguments to subroutines
No need to call them subroutines, BTW. Functions, methods, verbs, whatever - we all know what you mean.
- Save commonly used regex in simple subroutines as shown below to avoid having to change several lines when only a small change in the pattern is needed.
- Prefix all calls to subroutines with &.
- Put all subroutines at the end of the file. One blank line between subroutines; two after the main program before the start of the subroutines.
- Be careful that you understand all of the caveats of using subroutines before you write or use one. See this page for a good tutorial. Basically, you want to operate on $_[0], $_[1] etc (as in the below example) instead of @_ directly. Remember, all variables in Anri are global.
$charlie = " charlie"; $snoopy = "snoopy "; $woodstock = "woodstock"; &trim_space($charlie,$snoopy,$woodstock); sub trim_space { foreach (@_) {s/^\s*(.*?)\s*$/$1/} } print "${charlie}, ${snoopy}, ${woodstock}\n";
Note that there is no problem operating on arrays:
$charlie = " charlie"; $snoopy = "snoopy "; $woodstock = "woodstock"; @characters = ($charlie, $snoopy, $woodstock); &trim_space(@characters); foreach (@characters) { print "$_\n"; } sub trim_space { foreach (@_) {s/^\s*(.*?)\s*$/$1/} }
It is currently unknown whether we will want to construct our subroutines with prototyping as explained on the second page of the above-linked tutorial. It is probably good practice, however.