2013-07-29 15 views
0

我有這樣的代碼數字,並且我得到了警告:Argument "" isn't numeric in numeric eq (==)$id == $_論證「」是不是在數字EQ(==)

@delete已經數從網頁表單來(CGI請求),可能這就是爲什麼perl將這些數字視爲字符串。它工作正常,但我不知道該如何處理警告。

my @IDs = (21, 36, 6, 7, 64, 6435, 24); 
for my $id (@IDs) { 
    push @insert, $id if (grep $id == $_, @delete) 
} 

我不想警告。我最好的選擇是什麼?

我首先想到遍歷數組,併爲每個元素調用int,但我不喜歡這個想法。

回答

2

...這就是爲什麼perl將這些數字視爲字符串

不,Perl會將您的數據轉換爲數字,因爲數字相等運算符==。當它警告""時,這意味着你有一個空字符串,它將被轉換爲零0。換句話說,你的@delete數組包含一個空元素。

什麼你應該做的,而不是是使用哈希:

my @IDs = (21, 36, 6, 7, 64, 6435, 24); 
my %ID = map { $_ => 1 } @IDs; 
my @insert = grep $ID{$_}, @delete; 

這將避免任何轉換,它可以既是好事又是壞的。首先,它不會將空字符串轉換爲零,但它也不會將字符串" 12"轉換爲數字12

您的空字符串問題將保留,但只要您沒有空字符串的鍵,您就可以。

另外,你應該記住他們爲什麼被稱爲「警告」。他們在那裏表明你正在做一些不太正確的事情。所以只是在不知道爲什麼是一件非常糟糕的事情的情況下沉默警告。在這種情況下,你應該特別指出你想用空字符串值做什麼。 (和其他可能的錯誤值)。

你可以這樣做從數組中刪除空字符串值:

@delete = grep !/^$/, @delete; 
+0

哪種方法更好? '@delete = grep!/^$ /,@delete;' 或 '@delete = grep!$ _,@delete;' 很好的解釋。清除了很多疑問。 – GrSrv

+1

謝謝。那麼,在這種情況下'!/^$ /'和'!$ _'做相反的事情。空字符串是一個錯誤的值,所以否定它是真的。但是,執行真/假也是危險的,因爲它可能產生錯誤的否定(如果零'0'是有效值)以及誤報(例如字母或空格)。如果你從網絡表單獲得你的價值,你應該首先徹底驗證它們。在這種情況下,第一個更安全,因爲它只做一件事:檢查字符串是否爲空。 – TLP

3

如果0不是一個有效的ID,使用grep的syntaxt這樣的:

grep { $_ and ($id == $_) } @delete; 

或者,如果匹配$ _只有數字:

grep { /\d+/ and ($id == $_) } @delete; 
2

你的問題的快速演示:

use strict; 
use warnings; 

my @insert; 
my @IDs = (21, 36, 6, 7, 64, 6435, 24); 

my @delete = split//, "1 2 4"; 
warn "this is ok"; 
for my $id (@IDs) { push @insert, $id if (grep { $id == $_ } @delete) } 

warn "now get warning"; 
@delete = split//, "1 2 4"; 
#      ^^ note two spaces - the split will produce one empty element 
for my $id (@IDs) { push @insert, $id if (grep { $id == $_ } @delete) } 

您需要驗證您的輸入僅爲數字。

相關問題