我必須做的功能,將作爲標量和數組工作。例如:標量或數組函數
@t = testfunc(1, 2, 3, 4);
$x = testfunc(1, 2, 3, 4);
有人知道我該怎麼做嗎? 它必須打印「標量」如果它是$ x並打印「數組」如果@t。我試圖做這樣的事情:
sub testfunc()
{
print "test";
}
但是,即使這不工作:/
我必須做的功能,將作爲標量和數組工作。例如:標量或數組函數
@t = testfunc(1, 2, 3, 4);
$x = testfunc(1, 2, 3, 4);
有人知道我該怎麼做嗎? 它必須打印「標量」如果它是$ x並打印「數組」如果@t。我試圖做這樣的事情:
sub testfunc()
{
print "test";
}
但是,即使這不工作:/
此功能被命名爲「呼叫內容」。使用wantarray關鍵字。
@t = testfunc(1, 2, 3, 4);
$x = testfunc(1, 2, 3, 4);
sub testfunc {
if (wantarray) {
print "List context\n";
}
# False, but defined
elsif (defined wantarray) {
print "Scalar context\n";
}
# False and undefined
else {
print "Void context\n";
}
}
有Perl編寫的函數調用wantarray
返回:
true
如果子在一個列表上下文稱爲false
如果標undef
如果兩者都不是。舉個例子:
use strict;
use warnings;
sub wantarray_test {
if (not defined wantarray()) {
print "Called in void context by ", caller(), "\n";
}
else {
if (wantarray()) {
print "Called in list context by ", caller(), "\n";
return ("A", "list", "of", "results");
}
else {
print "called in a scalar context by ", caller(), "\n";
return "scalar result";
}
}
}
my @result = wantarray_test();
print "@result\n";
my $result = wantarray_test();
print $result, "\n";
wantarray_test();
獎金的問題:
你覺得你會得到,如果你:
print wantarray_test();
你可以做,如果比這更你很喜歡Contextual::Return
- 這將允許你測試更詳細的上下文,如scalar
和012之間的差異。 (這很有用,例如,如果你想測試一個百分比 - 你可能不想把'0'看作'假')。
但是請注意與上下文相關的功能。建立一些意想不到的行爲是很容易的,這可能會嚴重影響你的工作。
作爲一個相關的說明 - 你不應該聲明你的子。 perl中有一個稱爲原型的機制,它定義了你的子程序期望的參數類型。請參閱:perlsub
。你不應該定義你的子:
sub testfunc()
{
# some stuff
}
這指定了一個原型,應該避免,除非你確定這是你想要的。
使用wantarray功能
#!/usr/bin/env perl
use strict;
use warnings;
use feature 'say';
say my $x = testfunc(1,2,3,4);
say my @x = testfunc(1,2,3,4);
sub testfunc {
return wantarray ? @_ : "@_";
}
詭異的命名wantarray
是標準的做法 - 它可以讓你列表和標量上下文之間進行區分。您也可以使用CPAN中的Want
,它比標準的wantarray
內置函數稍差(請參閱Want
documentation)。
下應返回相同的結果wantarray
解決方案:
use Want;
sub testfuncadelic {
if (want('LIST')) {
rreturn @_; }
elsif (want('SCALAR')) {
rreturn "@_" ; }
return
}
下應剪切並粘貼到一個shell作爲一個僞「oneliner」(Unix的語法)證明:
% cpanm Want
% perl -MWant -E '
sub testfunc {
if (want("LIST")) {
rreturn "array in list context ", @_;}
elsif (want("SCALAR")) {
rreturn "string in scalar context @_"; }
return }
$result = testfunc(qw/1 2 3 4/); say $result;
@results = testfunc(qw/1 2 3 4/); say @results;'
輸出
string in scalar context 1 2 3 4
array in list context 1234
編輯
@Sobrique對這裏的標準方法有最徹底的處理 - 如果我問了這個問題,他/她會得到我的接受。我上面忽略的一件事是(如果wantarray
是undef
那麼顯然是'doh!),那麼你有無效的上下文!也許我假設這一點,並沒有意識到它可以明確用於檢測無效contxt。因此wantarray
可以爲您提供全部三種標準調用上下文。另一方面Wanted
是關於棘手的有趣的東西,我不是暗示它應該使用而是的wantarray
。我仍然認爲wantarray
應該有一個更好的名稱:-)
正如其他人已經指出,你會使用'wantarray'這個。請參閱'perldoc -f wantarray' http://perldoc.perl.org/functions/wantarray.html – shawnhcorey
不要使用原型(子名稱後的空括號)。它們的用法是* only *來覆蓋正常的子例程功能,以創建模仿某些內置插件行爲的模糊事物。 – TLP
@TLP:除非你有5.20+並且已經啓用了實驗簽名(但是即使在這種情況下,'()'也不適合) – ysth