将运算符作为参数变量

时间:2019-06-05 03:27:50

标签: perl

嗨,我正在尝试创建一个只有四个运算符+, -, /*的简单计算器,由于某种原因,我的实现无法正常工作。

我已经看到了几种可行的实现方式(包括一些值得混淆的地方),但是我很好奇的是为什么接下来的工作?

#!/usr/bin/perl

my $num1 = $ARGV[0];
my $num2 = $ARGV[2];

my $operator = $ARGV[1];

print "$operator \n";

if($operator == '-')
{
  $num3 = $num1 - $num2;
  print "$num1 - $num2 = $num3\n";
} 
elsif($operator == "+")
{
  $num3 = $num1 + $num2;
  print "$num1 + $num2 = $num3\n";
}
elsif($operator == "/")
{
  $num3 = $num1 / $num2;
  print "$num1 / $num2 = $num3\n";
}
elsif($operator == "*")
{
  $num3 = $num1 * $num2;
  print "$num1 * $num2 = $num3\n";
}

此外,命令./expr.pl 7 * 2返回以下内容:03.bellpaper.doc这是难以理解的。

3 个答案:

答案 0 :(得分:5)

始终使用来启动文件

use strict;
use warnings;

首先出现的结果是

Global symbol "$num3" requires explicit package name (did you forget to declare "my $num3"?) at script line 14.

添加缺少的my $num3声明后,我们得到

Argument "-" isn't numeric in numeric eq (==) at script line 13.

之所以会这样,是因为==运算符是数字相等的。它将两个操作数都转换为一个数字,如果您不启用警告,则该数字将以静默方式给出0来表示无效字符串。这就是($operand == '-')最终完成0 == 0的原因,这是正确的。

要比较字符串,您需要使用eq

if ($operand eq '-')

另请参阅Relational Operators in perldoc perlop

./expr.pl 7 * 2的问题在于*是一个通配符,您的Shell会扩展为当前目录中所有文件的列表。您的程序将以./expr.pl 7 03.bellpaper.doc expr.pl whatever-else-is-in-the-current-directory 2的形式调用。

为防止这种情况,您需要引用它,例如./expr.pl 7 '*' 2./expr.pl 7 "*" 2./expr.pl 7 \* 2


其他说明:

  • $operand是错误的名称。是操作员。这两个数字是操作数。
  • 可以将$ARGV[...]中的手动分配合并到一个列表分配中:my (...) = @ARGV;
  • 每个块中的print语句几乎相同。我们可以将它们拉出为print "$num1 $operator $num2 = $num3\n"(确保已实际设置$num3之后)。

这给了我们

#!/usr/bin/perl
use strict;
use warnings;

my ($num1, $operator, $num2) = @ARGV;

print "$operator\n";

my $num3;
if ($operator eq '-') {
    $num3 = $num1 - $num2;
} elsif ($operator eq '+') {
    $num3 = $num1 + $num2;
} elsif ($operator eq '/') {
    $num3 = $num1 / $num2;
} elsif ($operator eq '*') {
    $num3 = $num1 * $num2;
}

if (defined $num3) {
    print "$num1 $operator $num2 = $num3\n";
}

答案 1 :(得分:3)

  

此外,命令./expr.pl 7 * 2返回以下内容:03.bellpaper.doc,这简直不可思议。

*是一个外壳程序。您的外壳将*替换为当前目录中每个文件的名称。程序的参数是7,然后是许多文件名,然后是2。这些文件名中的第一个通过您的print "$operand\n"行打印,然后由于$operand与您要检查的任何内容都不匹配,因此不会发生其他任何事情。

解决此问题的方法只是在引号*周围加上引号,或采用命令行以外的其他方式输入内容。

答案 2 :(得分:0)

通常,当我在做这类事情时,我将创建一个称为choice的整数变量,该整数变量将被传递给方法。在方法中,我将拥有if和else if语句来解释参数。例如:0 = +,1 =-,2 = /和3 = *