perl学习笔记之:模式匹配,模块,文档

Perl语言的最大特点,也是Perl作为CGI首选语言的最大特点,是它的模式匹配操作符。Perl语言的强大的文本处理能力正是通过其内嵌的对模式匹配的支持体现的。模式通过创建正则表达式实现。Perl的正则表达式与模式匹配的特点一是内嵌于语言之中,而不是通过库或函数来实现,因此使用更简便;二是比一般的正则表达式与模式匹配功能强大。

模式匹配操作符简介


操作符


意义


实例


=~


匹配(包含)


!~


不匹配(不包含)


m//


匹配


$haystack =~ m/needle/

$haystack =~ /needle/


s///


替换


$italiano =~ s/butter/olive oil/


tr///(y///)


转换


$rotate13 =~ tr/a-zA-Z/n-za-mN-ZA-M/


qr//


正则表达式

使用说明

l         注意区别记忆Perl的绑定操作符(=~)与AWK的相应操作符(AWK的绑定匹配操作符是 ~),Perl与AWK的否定匹配操作符相同(都是!~)

l         没有绑定操作符时,默认是对$_进行绑定:

/new life/ and /new civilizations/ (对$_进行两次查找)

s/suger/aspartame/  (对$_进行替换)

tr/ATCG/TAGC/    (对$_进行转换)

l         m//操作符前面的m可以省略,但是不省略可读性更好,建议不省略。

l         如果有绑定操作符=~,m//都省略也表示匹配:

print “matches” if $somestring =~ $somepattern; 等价于

print “matches” if $somestring =~ m/$somepattern/;

l         m//, s///, tr///, qr//操作符是引用操作符,你可以选择自己的分割符(与q//, qq//, qw//一样):

$path =~ s#/tmp#/var/tmp/scratch#

if  ($dir =~ m[/bin]) {

print “No binary directories please. /n”;

}

l         一个括号可与其它括号配合使用,可以用空格分开:

s(egg)<larva>

s(larva){pupa};

s[pupa]/imago/;

s (egg) <larva>;

l         如果一个模式成功匹配上,$`, $&, $’将被设置,分别表示匹配左边、匹配、匹配右边的字符串:

“hot cross buns” =~ /cross/;

print “Matched: <$`> $& <$’>/n”;   # Matched <hot > cross < buns>

l         模式模式后设置的特殊变量如下:


变量


含义


$`


匹配文本之前的文本


$&


匹配文本


$’


匹配文本之后的文本


$1、$2、$3


对应第1、2、3组捕获括号匹配的文本


$+


编号最大的括号匹配的文本


$^N


最后结束的括号匹配的文本


@-


目标文本中各匹配开始位置的偏移值数组


@+


目标文本中各匹配结束位置的偏移值数组


$^R


最后执行的嵌入代码的结果,如果嵌入代码结构作为条件语句的if部分,则不设定$^R

m//, s///和qr//都接受以下修饰符:


修饰符


意    


/i


进行忽略字母大小的匹配


/s


单行模式(让.号匹配换行符并且忽略过时的$*变量,点号通配模式)


/m


多行模式(让^和$匹配内含的换行符(/n)的之后与之前。如果目标字符串中没有“/n”字符或者模式中没有 ^ 或 $,则设定此修饰符没有任何效果)。

(增强的行锚点模式)


/x


宽松排列和注释模式(忽略空白符(除转义空白符之外)并且允许模式中的注释)


/o


仅编译一次模式,防止运行时重编译

例如:

m//w+:(/s+/w+)/s*/d+/;          # A word, colon, space, word, space, digits

m//w+: (/s+  /w+) /s* /d+/x;     # A word, colon, space, word, space, digits

m{

/w+;                     # Match a word and a column

(                        # (begin group)

/s+                  # Match one or more spaces.

/w+                 # Match another word

)                        # (end group)

/s*                      # Match zero or more spaces

/d+                      # Match some digits

}x;

$/ = "";     # "paragrep" mode

while (<>) {

while ( m{

/b           # start at a word boundary

(/w/S+)      # find a wordish chunk

(

/s+      # separated by some whitespace

/1       # and that chunk again

) +          # repeat ad lib

/b           # until another word word boundary

}xig

)  {

print "dup word ‘$1‘ at paragraph $. /n";

}

}

模式匹配操作符详解

7.3.1 m//操作符(匹配)

EXPR =~ m/PATTERN/cgimosx

EXPR =~ /PATTERN/cgimosx

EXPR =~ ?PATTERN?cgimosx

m/PATTERN/cgimosx

/PATTERN/cgimosx

?PATTERN?cgimosx

说明:

l         如果PATTERN是空字符串,最后成功执行的正则表达式将被代替使用。

l         m//特殊修饰符如下:


修饰符


意    


/g


查找所有的匹配


/cg


在/g 匹配失败后允许继续搜索

l         在LIST上下文中m//g返回所有匹配

if (@perls = $paragraph =~ /perl/gi) {

printf “Perl mentioned %d times./n”, scalar @perls;

}

l         ??分隔符表示一次性匹配, ‘’分隔符压制变量替换和/U等六个转换

open DICT, "/usr/share/dict/words"  or die "Cannot open words: $!/n";

while (<DICT>) {

$first = $1 if ?(^love.*)?;

$last  = $1 if /(^love.*)/;

}

print $first, "/n";

print $last, "/n";

7.3.2 s///操作符(替换)

LVALUE =~ s/PATTERN/REPLACEMENT/egimosx

s/PATTERN/REPLACEMENT/egimosx

说明:

l         该操作符在字符串中查找PATTERN, 如果查找到,用REPLACEMENT代替匹配的子串。返回值是成功替换的次数(加/g修饰符可能大于1)。若失败,返回””(0)。

if ($lotr =~ s/Bilbo/Frodo/) { print “Successfully wrote sequel. “ }

$change_count = $lotr =~ s/Bilbo/Frodo/g;

l         替换部分作为双引字符串,可以使用动态生成的模式变量($`,$&, $’, $1, $2等):

s/revision/version/release//u$&/g;

s/version ([0-9.]+)/the $Names{$1} release/g;

l         如果PATTERN是空字符串,最后成功执行的正则表达式将被代替使用。PATTERN和REPLACEMENT都需进行变量替换,但是PATTERN在s///作为一个整体处理的时候替换,而REPLACEMENT在每次模式匹配到时替换。

l         s///特殊修饰符如下:


修饰符


意    


/g


替换所有的匹配


/e


将右边部分作为一个Perl表达式(代码)而不是字符串

/e修饰符的实例:

s/[0-9]+/sprintf(“%#x”, $1)/ge

s{

version

/s+

(

[0-9.]+

)

}{

$Names{$1}

? “the $Names{$1} release”

: $&

}xge;

l         不替换原字符串的方式:

$lotr = $hobbit;

$lotr =~ s/Bilbo/Frodo/g;

($lotr = $hobbit) =~ s/Bilbo/Frodo/g;

l         替换数组中的每一元素:

for (@chapters) { s/Bilbo/Frodo/g }

s/Bilbo/Frodo/g for @chapters;

l         对某一字符串进行多次替换:

for ($string) {

s/^/s+//;

s//s+$//;

s//s+/ /g

}

for ($newshow = $oldshow) {

s/Fred/Homer/g;

s/Wilma/Marge/g;

s/Pebbles/Lisa/g;

s/Dino/Bart/g;

}

l         当一次全局替换不够的时的替换:

# put comma in the right places in an integer

1 while s/(/d)(/d/d/d)(?!/d)/$1,$2/;

# expand tabs to 8-column spacing

1 while s//t+/’ ‘ x (length($&)*8 – length($`)%8)/e;

# remove (nested (even deeply nested (like this))) remarks

1 while s//([^()]*/)//g;

# remove duplicate words (and triplicate ( and quadruplicate…))

1 while s//b(/w+) /1/b/$1/gi;

7.3.3 tr///操作符(字译)

LVALUE =~ tr/SEARCHLIST/REPLACELIST/cds

tr/SEARCHLIST/REPLACELIST/cds

使用说明:

l         tr///的修饰符如下:


修饰符


意    


/c


补替换 (Complement SEARCHLIST)


/d


删除找到未替换的字符串(在SEARCHLIST中存在在REPLACELIST中不存在的字符)


/s


将重复替换的字符变成一个

l         如果使用了/d修饰符,REPLACEMENTLIST总是解释为明白写出的字符串,否则,如果REPLACEMENTLIST比SEARCHLIST短,最后的字符将被复制直到足够长,如果REPLACEMENTLIST为空,等价于SEARCHLIST,这种用法在想对字符进行统计而不改变时有用,在用/s修饰符压扁字符时有用。

tr/aeiou/!/;        # change any vowel into !

tr{////r/n/b/f. }{_};  # change strange chars into an underscore

tr/A-Z/a-z/ for @ARGV;   # canonicalize to lowercase ASCII

$count = ($para =~ tr//n//);

$count = tr/0-9//;

$word =~ tr/a-zA-Z//s;     # bookkeeper -> bokeper

tr/@$%*//d;             # delete any of those

tr#A-Za-z0-9+/##cd;      # remove non-base64 chars

# change en passant

($HOST = $host) =~ tr/a-z/A-Z/;

$pathname =~ tr/a-zA-Z/_/cs;  # change non-(ASCII) alphas to single underbar

元字符

Perl元字符有:

/ | ( ) [ { ^ $ * + ?

正则表达式元字符的意义如下:


Symbol


Atomic


Meaning


/...


Varies


转义


...|...


No


选择


(...)


Yes


集群(作为一个单位)


[...]


Yes


字符集合


^


No


字符串开始


.


Yes


匹配一个字符(一般除换行符外)


$


No


字符串结尾(或者换行符之前)

* + ?是数量元字符,Perl数量相关元字符意义如下:


Quantifier


Atomic


Meaning


*


No


匹配0或多次(最大匹配),相当于{0,}


+


No


匹配1或多次(最大匹配),相当于{1,}


?


No


匹配1或0次(最大匹配),相当于{0,1}


{COUNT}


No


匹配精确COUNT


{MIN,}


No


匹配最少MIN次 (最大匹配)


{MIN,MAX}


No


匹配最小MIN最大MAX次(最大匹配)


*?


No


匹配0或多次(最小匹配)


+?


No


匹配1或多次(最小匹配)


??


No


匹配1或0次(最小匹配)


{MIN,}?


No


匹配最少MIN次 (最小匹配)


{MIN,MAX}?


No


匹配最小MIN最大MAX次(最小匹配)

扩展正则表达式序列如下:


Extension


Atomic


Meaning


(?#...)


No


Comment, discard.


(?:...)


Yes


Cluster-only parentheses, no capturing.


(?imsx-imsx)


No


Enable/disable pattern modifiers.


(?imsx-imsx:...)


Yes


Cluster-only parentheses plus modifiers.


(?=...)


No


True if lookahead assertion succeeds.


(?!...)


No


True if lookahead assertion fails.


(?<=...)


No


True if lookbehind assertion succeeds.


(?<!...)


No


True if lookbehind assertion fails.


(?>...)


Yes


Match nonbacktracking subpattern.


(?{...})


No


Execute embedded Perl code.


(??{...})


Yes


Match regex from embedded Perl code.


(?(...)...|...)


Yes


Match with if-then-else pattern.


(?(...)...)


Yes


Match with if-then pattern.

说明:以上定义了向前查找(?=PATTERN),负向前查找(?!PATTERN),向后查找(?<=PATTERN),负向后查找(?<!PATTERN),条件查找等较为高级的正则表达式匹配功能,需要使用时请查阅相关资料。

字母顺序元字符意义:


Symbol


Atomic


Meaning


/0


Yes


Match the null character (ASCII NUL).


/NNN


Yes


Match the character given in octal, up to /377.


/n


Yes


Match nth previously captured string (decimal).


/a


Yes


Match the alarm character (BEL).


/A


No


True at the beginning of a string.


/b


Yes


Match the backspace character (BS).


/b


No


True at word boundary.


/B


No


True when not at word boundary.


/cX


Yes


Match the control character Control-X (/cZ, /c[, etc.).


/C


Yes


Match one byte (C char) even in utf8 (dangerous).


/d


Yes


Match any digit character.


/D


Yes


Match any nondigit character.


/e


Yes


Match the escape character (ASCII ESC, not backslash).


/E


--


End case (/L, /U) or metaquote (/Q) translation.


/f


Yes


Match the form feed character (FF).


/G


No


True at end-of-match position of prior m//g.


/l


--


Lowercase the next character only.


/L


--


Lowercase till /E.


/n


Yes


Match the newline character (usually NL, but CR on Macs).


/N{NAME}


Yes


Match the named char (/N{greek:Sigma}).


/p{PROP}


Yes


Match any character with the named property.


/P{PROP}


Yes


Match any character without the named property.


/Q


--


Quote (de-meta) metacharacters till /E.


/r


Yes


Match the return character (usually CR, but NL on Macs).


/s


Yes


Match any whitespace character.


/S


Yes


Match any nonwhitespace character.


/t


Yes


Match the tab character (HT).


/u


--


Titlecase next character only.


/U


--


Uppercase (not titlecase) till /E.


/w


Yes


Match any "word" character (alphanumerics plus "_").


/W


Yes


Match any nonword character.


/x{abcd}


Yes


Match the character given in hexadecimal.


/X


Yes


Match Unicode "combining character sequence" string.


/z


No


True at end of string only.


/Z


No


True at end of string or before optional newline.

(以上均直接Copy自《Programming Perl》,下面未翻译者同)

其中应注意以下经典的字符集合:


Symbol


Meaning


As Bytes


As utf8


/d


Digit


[0-9]


/p{IsDigit}


/D


Nondigit


[^0-9]


/P{IsDigit}


/s


Whitespace


[ /t/n/r/f]


/p{IsSpace}


/S


Nonwhitespace


[^ /t/n/r/f]


/P{IsSpace}


/w


Word character


[a-zA-Z0-9_]


/p{IsWord}


/W


Non-(word character)


[^a-zA-Z0-9_]


/P{IsWord}

POSIX风格的字符类如下:


Class


Meaning


alnum


Any alphanumeric, that is, an alpha or a digit.


alpha


Any letter. (That‘s a lot more letters than you think, unless you‘re thinking Unicode, in which case it‘s still a lot.)


ascii


Any character with an ordinal value between 0 and 127.


cntrl


Any control character. Usually characters that don‘t produce output as such, but instead control the terminal somehow; for example, newline, form feed, and backspace are all control characters. Characters with an ord value less than 32 are most often classified as control characters.


digit


A character representing a decimal digit, such as 0 to 9. (Includes other characters under Unicode.) Equivalent to /d.


graph


Any alphanumeric or punctuation character.


lower


A lowercase letter.


print


Any alphanumeric or punctuation character or space.


punct


Any punctuation character.


space


Any space character. Includes tab, newline, form feed, and carriage return (and a lot more under Unicode.) Equivalent to /s.


upper


Any uppercase (or titlecase) letter.


word


Any identifier character, either an alnum or underline.


xdigit


Any hexadecimal digit. Though this may seem silly ([0-9a-fA-F] works just fine), it is included for completeness.

注意:POSIX风格字符类的使用方法,

42 =~ /^[[:digit:]]+$/  (正确)

42 =~ /^[:digit:]$/   (错误)

这里使用的模式以[[开头,以]]结束,这是使用POSIX字符类的正确使用方法。我们使用的字符类是[:digit:]。外层的[]用来定义一个字符集合,内层的[]字符是POSIX字符类的组成部分。

常见问题的正则解决方案

IP地址

(((/d{1,2})|(1/d{2})|(2[0-4]/d)|(25[0-5]))/.){3}((/d{1,2})|(1/d{2})|(2[0-4]/d)|(25[0-5]))

邮件地址

(/w+/.)*/[email protected](/w+/.)+[A-Za-z]+

(以上邮件地址正则表达式并非严格的,但是可以匹配绝大多数普通的邮件地址。

HTTP URL:

{http://([^/:]+)(:(/d+))?(/.*)?$}i

https?://(/w*:/w*@)?[-/w.]+(:/d+)?(/([/w/_.]*(/?/S+)?)?)?

C语言注释

/

在Perl中,类、包、模块是相关的,一个模块只是以同样文件名(带.pm后缀)的一个包;一个类就是一个包;一个对象是一个引用;一个方法就是一个子程序。这里只说明其最简单的使用方法。

模块使用

以下是一个模块(Bestiary.pm)的编写方式,可以作为写一般模块的参考。

package      Bestiary;
require      Exporter;
 
our @ISA       = qw(Exporter);
our @EXPORT    = qw(camel);    # Symbols to be exported by default
our @EXPORT_OK = qw($weight);  # Symbols to be exported on request
our $VERSION   = 1.00;         # Version number
 
### Include your variables and functions here
 
sub camel { print "One-hump dromedary" }
 
$weight = 1024;
 
1;
(引自《Programming Perl》)

对象使用

以下例子用来构建一个Ipregion对象,可以使用该对象的get_area_isp_id方法查找一个IP的地区与运营商。本例可以作为写一般对象的参考。

package Ipregion;

use strict;

my ($DEFAULT_AREA_ID, $DEFAULT_ISP_ID) = (999999, 9);

my ($START_IP, $END_IP, $AREA_ID, $ISP_ID) = (0 .. 3);

sub new {

my $invocant = shift;

my $ip_region_file = shift;

my $class = ref($invocant) || $invocant;

my $self = [ ];                     # $self is an reference of array of arrays

# Read into ip region data from file

open my $fh_ip_region, ‘<‘, $ip_region_file

or  die "Cannot open $ip_region_file to load ip region data $!";

my $i = 0;

while (<$fh_ip_region>) {

chomp;

my ($start_ip, $end_ip, $area_id, $isp_id) = split;

$self->[$i++] = [ $start_ip, $end_ip, $area_id, $isp_id ];

}

bless($self, $class);

return $self;

}

sub get_area_isp_id {

my $self        = shift;

my $ip          = shift;

my $area_id = $DEFAULT_AREA_ID;

my $isp_id     = $DEFAULT_ISP_ID;

# Check if a ip address is in the table using binary search method.

my $left  = 0;

my $right       = @$self - 1;                   # Get max array index

my $middle;

while ($left <= $right) {

$middle = int( ($left + $right) / 2 );

if ( ($self->[$middle][$START_IP] <= $ip) && ($ip <= $self->[$middle][$END_IP]) ) {

$area_id = $self->[$middle][$AREA_ID];

$isp_id  = $self->[$middle][$ISP_ID];

last;

}

elsif ($ip < $self->[$middle][$START_IP]) {

$right = $middle - 1;

}

else {

$left = $middle + 1;

}

}

return ($area_id, $isp_id);

}

该对象的使用方法是:

use Ipregion;

my $ip_region = Ipregion->new("new_ip_region.dat");

my @search_result = $ip_region->get_area_isp_id(974173694);

.Perl特殊变量


变量符号(名)


意  


$a


sort函数使用存储第一个将比较的值


$b


sort函数使用存储第二个将比较的值


$_ ($ARG)


默认的输入或模式搜索空间


@_ (@ARG)


子程序中默认存储传入参数


ARGV


The special filehandle that iterates over command-line filenames in @ARGV


$ARGV


Contains the name of the current file when reading from ARGV filehandle


@ARGV


The array containing the command-line arguments intended for script


$^T ($BASETIME)


The time at which the script began running, in seconds since the epoch


$? ($CHILD_ERROR)


The status returned by the last pipe close, backtick(``)command, or wait, waitpid, or system functions.


DATA


This special filehandle refers to anything following the __END__ or the __DATA__ token in the current file


$)  ($EGID,

$EFFECTIVE_GROUP_ID)


The effective GID of this process


$> ($EUID,

$EFFECTIVE_USER_ID)


The effective UID of this process as returned by the geteuid(2) syscall


%ENV


The hash containing your current environment variables


[email protected] ($EVAL_ERROR)


The currently raised exception or the Perl syntax error message from the last eval operation


@EXPORT


Exporter模块import方法使用


@EXPORT_OK


Exporter模块import方法使用


%EXPORT_TAGS


Exporter模块import方法使用


%INC


The hash containing entries for the filename of each Perl file loaded via do FILE, require or use


@INC


The array containing the list of directories where Perl module may be found by do FILE, require or use


$. ($NR,

 $INPUT_LINE_NUMBER)


The current record number (usually line numberZ) for the last filehandle you read from.


$/ ($RS,

$INPUT_RECORD_SEPARATOR)


The input record separator, newline by default, which is consulted by the readline function, the <FH> operator, and the chomp function.

$/=””将使得记录分割符为空白行,不同于”/n/n”

undef $/; 文件剩余所有行将全部一次读入

$/=/$number将一次读入$number字节


@ISA


This array contains names of other packages to look through when a method call cannot be found in the current package


@+ @- $` $’ $& $1 $2 $3


匹配相关变量


$^ $~ $|


Filehandle相关


$” ($LIST_SEPARATOR)


When an array or slice is interpolated into a double-quoted string, this variable specifies the string to put between individual elements. Default is space.


$^O ($OSNAME)


存储平台名


$! ($ERRNO, $OS_ERROR)


数值上下文:最近一次调用的返回值

字符串上下文:响应系统错误信息


$, ($OFS,

$OUTPUT_FIELD_SEPARATOR)


print的字段分割符(默认为空)


$/($ORS,

$OUTPUT_RECORD_SEPARATOR)


print的记录分割符(默认为空,设为”/n”是很好的选择)


$$ ($PID)


The process number


$0 ($PROGRAM_NAME)


程序名


$( ($GID, $PEAL_GROUP_ID)


进程的真正GID


$< ($UID, $PEAL_USER_ID)


%SIG


The hash used to set signal handlers for various signals


STDERR


标准错误Filehandle


STDIN


标准输入Filehandle


STDOUT


标准输出Filehandle


$; $SUBSEP

$SUBSCRIPT_SEPARATOR


The subscript sesparator for multidimensional hash emulation

$foo{$a,$b,$c}=$foo{join($;,$a,$b,$c)}

说明:若需要使用长文件名,必须使用use English;

程序文档(POD)

POD(Plain Old Documentation), 它是一种简单而易用的标记型语言(置标语言),用于perl程序和模块中的文档书写。POD中用段分可以分为三种,普通段落,字面段落(Verbatim Paragraph)和命令段落。三者的区分非常简单,以=pod|head1|cut|over等指示字开始的段落为命令段落,以空格或制表符(/t)等缩进开始的段落为字面段落,其余的就是普通段落。POD中有其独特的格式代码来表现粗体,斜体,超链接等。

POD使得Perl语言的文档编写易于完成,程序说明文档与程序源代码同时存在。可以用以下解释器解释POD: pod2text、pod2man (pod2man File.pm |nroff –man |more)、pod2html、pod2latex。

一般建议对源代码包括以下部分的POD文档:

=head1 NAME

The name of your program or module.

=head1 SYNOPSIS

A one-line description of what your program or module does (purportedly).

=head1 DESCRIPTION

The bulk of your documentation. (Bulk is good in this context.)

=head1 AUTHOR

Who you are. (Or an alias, if you are ashamed of your program.)

=head1 BUGS

What you did wrong (and why it wasn‘t really your fault).

=head1 SEE ALSO

Where people can find related information (so they can work around your bugs).

=head1 COPYRIGHT

The copyright statement. If you wish to assert an explicit copyright, you should say something like:

Copyright 2013, Randy Waterhouse.  All Rights Reserved.

Many modules also add:

This program is free software.  You may copy or

redistribute it under the same terms as Perl itself.

编程风格

为了使程序易于阅读、理解和维护,建议使用以下编程风格(以下建议均为Larry Wall在perlstyle文档中所写,其实许多条对于其它语言编程也适用):

l         多行BLOCK的收尾括号应该跟结构开始的关键字对齐;

l         4列的缩进;

l         开始括号与关键字同一行,如果可能的话,否则,与关键字对齐;

l         在多行BLOCK的开始括号之前留空格;

l         一行的BLOCK可以写在一行中,包括括号;

l         在分号前不留空格;

l         分号在短的一行BLOCK中省略;

l         在大多数操作符两边留空格;

l         在复杂的下标两边加空格(在方括号内);

l         在做不同事情的代码段中留空行;

l         不连接在一起的else;

l         在函数名和开始的括号之间不加空格;

l         在每一逗号后加空格;

l         长行在操作符后断开(除了and和or外)

l         在本行匹配的最后的括号后加空格

l         相应项竖直对齐

l         只要清晰性不受损害省略冗余的标点符号

l         你能怎样做不意味着你应该怎样做。Perl设计来给予你做任何事的多种方法,所以选择最易读的方法。

open(FOO, $foo) || die “Cannot open $foo: $!”;

比 die “Cann’t open $foo: $!” u;nless open(FOO, $foo)

l         不要害怕使用循环标号,它们可以增强可读性并且允许多层循环跳出。

l         选择易于理解的标示符。如果你不能记住你的记忆法,你将碰到问题

l         在使用长标示符时用下划线分隔单词

l         在使用复杂的正则表达式时使用/x

l         使用here文档而不是重复的print()语句

l         垂直对齐相应的东西,特别是在一行不能容下时

l         总是检查系统调用的返回值。好的错误信息应该输出的标准错误输出,包括那一程序造成了问题的信息。

l         对齐转换的信息:

tr [abc]

[xyz]

l         考虑复用性,一般化你的代码,考虑写一个模块或者类。

l         使用POD文档化你的代码

l         保持一致

l         保持友好

参考文献

【1】Larry Wall, Tom Christiansen & Jon Orwant. Programming Perl. Third Edition (The Camel Book)

【2】Randal L. Schwartz, Tom Phoenix, and brian d foy. Learning Perl (The Llama Book )

【3】Damian Conway. Perl Best Practices(Perl 最佳实践—影印版). O’reilly. 东南大学出版社. 2006.4

【4】Ben Forta著.杨涛等译. 正则表达式必知必会.北京:人民邮电出版社. 2007.12

【5】Jeffrey E.F. Friedl著. 余晟译. 精通正则表达式(第3版).北京:电子工业出版社. 2007.7

【6】The perldoc mainpage

时间: 2024-10-12 20:14:46

perl学习笔记之:模式匹配,模块,文档的相关文章

Python学习笔记__8.4章 文档测试

# 这是学习廖雪峰老师python教程的学习笔记 1.概览 在文档中编写规范的注释代码.则Python内置的"文档测试"(doctest)模块可以直接提取注释中的代码并执行测试. 1.1.以abs()函数为例: #abs.py def abs(n): ''' # 两个为一对,换行输入 Function to get absolute value of number.  # 简单的介绍 Example: >>> abs(1)   # 测试 1 >>>

Elasticsearch学习笔记-04.1更新文档

除了创建和替换文档,我们也可以更新文档.需要注意的是Elasticsearch在底层并不会整的更新文档.当我们执行更新操作的时候,Elasticsearch会一次性完成先删除,再新建一个文档.下面的例子示意了如何将我们之前索引的ID为1的文档的name字段修改为"Jane Doe": POST /customer/external/1/_update?pretty { "doc": { "name": "Jane Doe" }

Elasticsearch学习笔记-04.2删除文档

删除文档非常的简单而直观.下面的例子示意了如何删除我们之前创建的ID为2的客户文档: DELETE /customer/external/2?pretty 要删除所有满足检索条件的文档可以参考 [Delete By Query API].不过这个API并没有太大价值,因为删除整个索引要比删除索引中的满足条件的所有的文档来的更高效. 本文系本人根据官方文档的翻译,能力有限.水平一般,如果对想学习Elasticsearch的朋友有帮助,将是本人的莫大荣幸. https://www.elastic.c

MongoDB快速入门学习笔记3 MongoDB的文档插入操作

1.文档的数据存储格式为BSON,类似于JSON.MongoDB插入数据时会检验数据中是否有“_id”域,如果没有会自动生成.shell操作有insert和save两种方法.当插入一条数据有“_id”值,并且现在集合中已经有相同的值,使用insert插入时插入不进去,使用save时,会更新数据. 1 > db.student.drop() 2 true 3 > db.student.insert({"_id": 1, "name":"zhang

JavaScript学习笔记7 之DOM文档对象模型

一.什么是DOMDocument Object Model 文档 -------对象 ----模型-------缩写DOM DOM是针对HTML和XML文档的一个API(应用程序编程接口).DOM描绘了一个层次化的节点树,允许开发人员添加.移除和修改页面的某一部分.DOM树中的所有节点均可通过JS进行访问.所有HTML元素(节点)均可被修改.创建或删除. 二.节点类型1.节点类型 HTML 文档中的所有内容都是节点(node): 整个文档是一个文档节点每个 HTML 元素是元素节点HTML 元素

php学习笔记之将word文档转化为HTML文件

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-

《DOM Scripting》学习笔记-——第八章 充实文档的内容

本章内容 一.一个为文档创建"缩略词语表"的函数 二.一个为文档创建"文献来源链接"的函数 三.一个为文档创建"快速访问键清单"的函数 利用DOM动态的收集和创建一些有用的辅助信息,并把它们呈现在网页上的基本思路: 1.把隐藏在属性里的信息检索出来(遍历.提取) 2.把这些信息动态的创建为一些html内容(创建元素节点.将内容插入元素节点) 3.把这些html内容插入到文档里(追加) Html代码: 1 <!DOCTYPE html PUB

HTML&amp;CSS基础学习笔记1.4-定义文档类型

Web 世界中存在许多不同的文档.只有了解文档的类型,浏览器才能正确地显示文档. HTML 也有多个不同的版本,只有完全明白页面中使用的确切 HTML 版本,浏览器才能完全正确地显示出 HTML 页面.这就是 <!DOCTYPE> 的用处. <!DOCTYPE> 声明不是 HTML 标签,它是指示 web 浏览器关于页面使用哪个 HTML 版本进行编写的指令.是一种标准通用标记语言的文档类型声明,它的目的是要告诉标准通用置标语言解析器,它应该使用什么样的文档类型定义来解析文档. &

HTML5 学习笔记四(跨文档消息通信)

一.同域 父→子  方法: ⒈iframe对象:父页面的iframe中的子页面,父的iframe对象的contentWindow即为子window对象. ⒉父通过window.open()方法,其方法接收子url作为参数,方法返回值为子window对象. 子→父 方法: ⒈iframe:在父页面的iframe中,子页面的parent(window.parent)对象为父window. ⒉使用open()方法的父子,其子页面的window.openner即为父window对象. 二.跨域 在父窗口

Python学习笔记#函数中使用文档,让你的函数更容易理解

>>> def intadd(a,b): 'this is a test of the doc of function' return a+b >>> intadd(2,3) 5 >>> intadd.__doc__ 'this is a test of the doc of function' >>>