只应定义两个参数中的一个

时间:2013-05-20 18:42:55

标签: perl

写下一个更优雅的方式是什么?

sub depend {
    my($x,$y) = @_;
    die "only one allowed" if( defined($x) && defined($y) );
    die "one must be defined" unless ( defined($x) || defined($y) );
    if( defined($x) ) {
         $y = somefunc($x);
    } else {
         $x = somefunc($y);
    }
    return($x,$y);
 }

该函数应该只获得一个参数。如果get define both = error,如果定义none = error。未定义的arg是根据定义的arg计算的。

4 个答案:

答案 0 :(得分:10)

使用xor,即“独占或”:

sub depend {
    my ($x, $y) = @_;
    die "Exactly one must be defined.\n" unless defined $x xor defined $y;

    if (defined $x) {
         $y = somefunc($x);
    } else {
         $x = somefunc($y);
    }
    return($x, $y);
 }

更新:您也可以缩短其余部分。而不是if部分,只需添加

return ($x // somefunc($y), $y // somefunc($x));

答案 1 :(得分:1)

我可以定义子例程来接受两个参数,但将它们视为键值对。要使用评论中的宽度/高度示例:

sub depend {
    my $key = shift;
    my $value = shift;
    die "One parameter only" if @_;
    return ($value, calc_height($value)) if $key eq "width";
    return (calc_width($value), $value) if $key eq "height";
    die "Must specify either height or width, not $key";
}

my ($w1, $h1) = depend( width => 5 );
my ($w2, $h2) = depend( height => 10 );
my ($w3, $h3) = depend();  # ERROR Must specify either height or width
my ($w4, $h4) = depend( other=>3 );  # ERROR Must specify either height or width, not other
my ($w5, $h5) = depend( foo => bar, 7); # ERROR, One parameter only

答案 2 :(得分:0)

试试这个:

sub f 
{
  my ($x, $y) = @_; 
  die "BOOM" if (defined $x ? 1 : 0) + 
                (defined $y ? 1 : 0) != 1;
}

答案 3 :(得分:-1)

使用xor可能不直观,下面的解决方案很容易扩展到更多输入参数,

 sub depend {
    my($x,$y) = @_;

    die "There should be only one!" if (grep defined, $x,$y) != 1;

    if( defined($x) ) {
         $y = somefunc($x);
    }
    else {
         $x = somefunc($y);
    }
    return($x,$y);
}