bash 脚本中的算术

bash 脚本中的算术

在 bash 脚本中,我想根据我的输入确定最大值或最小值:例如,如果我的输入是max 20 40,那么输出应该是40。如果输入为 ,min 20 40则输出应为20,对于任意两个数字依此类推。

加法、减法、乘法和除法也需要进行同样的操作。如果输入为6 + 6则输出为12。如果输入为6 * 6则输出为36

我遇到的问题是我能够告诉 bash 回显两个数字,然后显示最小值或最大值,甚至进行加减法等。例如,如果输入是5 10输出,则15如果我正在运行加法文件。但是我不明白如何在一行中完成所有操作,例如如果输入是5 + 10输出是15

我们现在可以忘记最大/最小运算,而专注于解决方案的算术部分。为了更好地解释这个问题,代码应按如下方式运行。

bash filename.sh
6 * 7
42

第一行是我运行文件,第二行是我输入输入的位置,最后一行是输出(答案),后面跟着一个新行。如果我只需要相乘6 * 7,这非常容易,但事实并非如此。运行文件bash filename.sh并单击 Enter 后,我应该被定向到下一行,我可以在其中输入任何简单的算术运算,仅限于加法、减法、乘法和除法。

有关代码应如何运行的更多示例

bash filename.sh
10+ 5
15
bash filename.sh
14 / 7
2
bash filename.sh 
17 - 3
14

该脚本应该能够对输入的任何值执行此操作,谢谢

答案1

这个问题可以分成两个简单的问题:

  1. 我怎样才能进行四次算术运算?
  2. 我怎么知道哪个数字更少/更大?

四种算术运算

您可以使用$((expr))符号来做到这一点。您可能想查看man bash更多信息。例子:

$ echo $((6 + 6))
12
$ echo $((6 * 6))
36

更少/更多数量

你可以比较两个数字s in[[ expr ]][ expr ]形式。我更喜欢[[ expr ]]形式,所以下面就是这种形式。比较数字,[[ $num1 -lt $num2 ]]如果$num1小于$num2。并-gt检查是否刨丝器。注意,-ltand-gt不能写成<and >;它们按字典顺序进行比较,而不是按数字顺序进行比较。

例子:

function max() {
  first=$1
  second=$2
  if [[ $first -lt $second ]]; then
    echo $second
  else
    echo $first
  fi
}

function min() {
  first=$1
  second=$2
  if [[ $first -gt $second ]]; then
    echo $second
  else
    echo $first
  fi
}

用法:

$ max 20 40
40
$ min 20 40
20

答案2

您的意思是在单行中打印输入和计算值吗?

以下是list.txt您的问题列表:

$ cat list.txt
1 + 2
3 + 4
5 + 10

calculating.sh你的脚本接受字符串输入,并打印出计算值(这里我只写了 + 操作)

$ cat calculating.sh
#!/bin/bash

varA=$(echo $1 | cut -d' ' -f1)
varB=$(echo $1 | cut -d' ' -f3)
operator=$(echo $1 | cut -d' ' -f2)

echo $(($varA + $varB))

list.txt要使用脚本计算每个条目,calculating.sh您可以执行以下操作:

$ cat list.txt | xargs -I {} sh -c "echo -n {} '= ' && ./calculating.sh '{}'"

1 + 2 = 2
3 + 4 = 6
5 + 10 = 10

xargs"echo -n {} '= ' && ./calculating.sh '{}'"使的每一行运行命令list.txt,其中{}指的是每一行(将其视为循环每一行)。echo -n {} =将使用 = 字符打印您的问题行,并且不使用换行符。然后./calculating.sh '{}'将打印计算出的值。

答案3

如果你想要一个快速而肮脏的表达式,你可以将输入的表达式推入 shell 的算术扩展中:

$ cat arith.sh
#!/bin/bash
read -r expr
if [[ $expr = *\$* || $expr = *\`* ]]; then
    echo "invalid entry!" >&2
    exit 1
fi
echo "$(($expr))"

然后例如

$ ./arith.sh 
(10+4)*5
70

该子句中的测试if拒绝包含美元符号或反引号的输入,因为它们可用于插入命令替换。无效的算术语法会从 shell 中给出错误。

对于比较,您可以使用 C 风格的比较运算符<// <=/>>=三元运算符,例如将给出和$((a > b ? a : b))的最大值。ab

max因此,要使用和扩展脚本min

$ cat arith2.sh
#!/bin/bash

read -r expr

if [[ $expr = *\$* || $expr = *\`* ]]; then
    echo "invalid entry!" >&2
    exit 1
fi

if [[ $expr = "max "* ]]; then
    read -r op a b <<< "$expr"
    echo "$((a > b ? a : b))"
elif [[ $expr = "min "* ]]; then
    read -r op a b <<< "$expr"
    echo "$((a < b ? a : b))"
else 
    echo "$(($expr))"
fi

max 1 2 3由于工作原理,这会破坏输入read,而且 Bash 不支持浮点数,因此它们也会给出错误。根据输入数据的来源,您可能需要考虑对其进行健全性检查。

相关内容