該博文將陸續列出本人編程過程當中出現一些錯誤,供你們參考。 正則表達式
一、輸出相反字符串
$a="abcde";
print reverse($a), "\n"; #輸出「abcde」
緣由:print要求列表,所以reverse把$a看成包含一個元素的列表,即($a),而後把該列表全部元素以相反順序返回。但因爲該列表只有一個元素,所以返回結果和原列表相同。
修正:使其處於標量上下文環境。方法至少有兩個。
print scalar reverse($a), "\n"; #使用scalar強行規定標量上下文
print reverse($a)."\n"; #使用字符串鏈接符將其置於標量上下文 編程
二、邏輯操做符的短路操做
opendir D1, "test" || die "no exist"; #當test不存在時,並無輸出出錯信息
緣由:"||"的優先級比較高,原句至關於opendir D1, ("test" || die "no exist");
修正:使用括號或使用or
opendir (D1, "test") || die "no exist";
opendir D1, "test" or die "no exist"; #我的認爲這個更好 ubuntu
三、比較操做符的正確使用
if (a == b) {print "true\n";} else {print "false\n";} #輸出true
緣由:'=='用於數字比較,字符比較應使用'eq'
修正:
if (a eq b) {print "true\n";} else {print "false\n";} #輸出false
#這個錯誤緣由很簡單,但犯了不止一次錯誤
#在這裏常常犯的另外一個錯誤是把'=='寫成'=' windows
四、while循環對$_的影響1
my @a=1..5;
for (@a) {
open FILEIN, '< ../temp';
while (<FILEIN>) {/A/;}
$_++;
}
print "@a\n"; #輸出"1 1 1 1 1"
緣由:多是while循環後沒有將$_恢復原值
將while換成for,則輸出"2 3 4 5 6"
不知道算不算bug
修正:根據具體狀況有多種修正方式
但最保險的是不要在while循環以後使用$_ 命令行
五、while循環對$_的影響2
my @a=0..9;
print @a,"\n"; #輸出"0123456789"
&Read(@a);
print "@a-end\n"; #輸出" -end"
sub Read {
for (@_) {
open FILE, '< temp';
/A/ while <FILE>;
}
}
緣由:仍然是while循環後$_沒有恢復原值,而while最後讀取的是結束標誌
同時$_和@_又能夠直接修改調用參數
修正:除非要修改調用參數
不然最好在子程序開始的時候將@_的內容賦予其餘變量
另:在使用use warnings時,會有警告信息。 scala
六、print的一個「異常」
環境:ubuntu12.04.1, perl 5.14.2, GNOME終端3.4.1.1
for (0..9) {
print $_;
sleep 1; #暫停1s
}
#10s內看不到任何輸出,10s後一次性輸出0123456789
緣由:命令行窗口一次輸出一行,而在循環結束之前這一行沒有結束
所以直到循環結束,才一次性輸出
修正:這個應該不是perl的問題
若想每一個循環都有輸出,加一個換行符便可。 字符串
七、windows下文本文件多餘的回車符
windows下文本文件的行尾是「\r\n",而chomp只能去掉最後的"\n"。
可以使用"s/\r//"將全部的"\r"刪掉。 test
八、shift的誤用
@a=1..10;
$a=shift @a if shift @a;
print "$a\n"; #輸出2
緣由:本意是若是能從@a中去除元素,則輸出該元素。
但其實是對@a進行了兩次shift操做。
修正:$a=shift @a if @a;
該錯誤一樣適用於pop、push、unshift。 變量
九、文件句柄沒有關閉致使的錯誤
程序:
open Fout, '> temp';
print Fout 1..10;
open Fin, '< temp';
my $a = <Fin>;
$a? print "yes\n" : print "null\n"; #輸出null
緣由:Fout沒有關閉,因此print的輸出尚未及時寫入文件,致使Fin調用時找不到內容。
修正:
方法1:及時關閉Fout。
open Fout, '> temp';
print Fout 1..10;
close Fout;
open Fin, '< temp';
my $a = <Fin>;
$a? print "yes\n" : print "null\n"; #輸出yes
方法2:兩個句柄同名
open Fout, '> temp';
print Fout 'a' x 10;
open Fout, '< temp';
my $a = <Fout>;
$a? print "yes\n" : print "null\n"; #輸出yes
注意:前面程序中,因爲往程序中寫入內容較少,因此所有內容都沒有寫入。但當寫入內容很是多時,會寫入部份內容,致使容易判斷錯誤。
open Fout, '> temp';
print Fout 'a' x 100000;
open Fin, '< temp';
my $a = <Fin>;
$a? print "yes\n" : print "null\n"; #輸出yes
print length($a),"\n" #輸入98304 perl
十、正則表達式非貪心匹配的誤用
程序:
my $_="123-456-789";
my $b=$1 if /-(.+?)$/; #想匹配789
print "$b\n"; #輸出456-789
緣由:正則表達式從左往右匹配,先找到第一個'-',而後逐個字符匹配直到字符串結尾
修正:my $b=$1 if /.+-(.+?)$/;
十一、三目操做符(條件操做符)的誤用 程序: my $a=1; $a? $a += 2 : $a -= 3; print "$a\n"; 輸出0 緣由:三目操做符的結果能夠賦值,如$a>$b? $a : $b = 0;(將較大的數賦值爲0) 所以原程序中的 ‘$a? $a += 2 : $a -= 3;’ 至關於 ‘($a? $a += 2 : $a) -= 3;’ 修正:$a? ($a += 2) : ($a -= 3);