在 bash 中添加和计算输入

在 bash 中添加和计算输入

如何制作一个 bash 脚本来添加并计算用户输入的数字数量?我不知道如何处理变量,因为用户可能会输入无限的输入。如果用户没有输入任何内容,则应该给出错误消息。这是我到目前为止的代码,它可能是错误的,所以对我来说放轻松,我仍然是一个初学者。

#!/bin/bash
if [ read = null ]
  echo "Invalid input."
else
  echo "please input numbers to add"
  #add numbers inputted
  read num1 num2 num3 num4 num5 num6 num7 
  #i put 7 variables but it needs to add however many numbers the user puts
  TOTAL=$((num1+num2+num3+num4+num5+num6+num7))
  #count how many numbers are inputted
  read num1 num2 num3 num4 num5 num6 num7
  wordCount=$((num1+num2+num3+num4+num5+num6+num7 | wc -c))
  echo "Your total is $TOTAL and the number of inputs you entered is $wordCount"\
fi

答案1

  1. 这条if [ read = null ]线纯属无稽之谈。这根本没有任何意义。

  2. 您使用的是 bash,因此您可以将数字读入数组,而不是固定数量的变量。

尝试这样的事情:

$ cat add.sh
#!/bin/bash

while true; do
  printf "Please input numbers to add: "
  read -r -a numbers

  # exit if input is empty
  [ "${#numbers[@]}" == 0 ] && break

  # check if input consists only of numbers
  # (integers or decimals allowed)
  for n in "${numbers[@]}"; do
    if ! [[ "$n" =~ ^[0-9]+(\.[0-9]+)?$ ]] ; then
      echo "Invalid input: $n"
      continue 2
    fi
  done

  expression="$(printf "%s+" "${numbers[@]}" | sed -e 's/+$//')"
  echo "$expression" | bc
done

该循环永远循环 ( while true),请求输入并将输入读入数组numbers

如果 中的元素数量numbers为零,则以 退出 while 循环break。顺便说一句,"${#numbers[@]}"返回数组中的元素数量 - 即您想要的“字数”。如果需要,您可以使用echo或打印此内容。printf我不会为你做所有的作业,所以我会把它留给你来做。

如果任何输入元素不是数字,它会打印“无效输入”并返回到 while 循环的开头(带有continue 2-2参数是必要的,因为此时脚本处于一个while循环和一个for循环内。如果没有2,它只会退出for循环,即它会打印“无效输入”,然后尝试执行计算)

否则,它使用 构造一个字符串(在名为 的变量中expressionprintfsed用于+从字符串末尾去除尾随。

然后将表达式通过管道传输到公元前,这是一个计算器工具。与 bash 内置的纯整数运算不同,bc它可以处理浮点数。 bc默认情况下,它可能不会安装在您的系统上,但如果您运行的是 Linux,则它应该作为软件包提供(例如,在 Debian 上,它位于软件包中bc)。它是 POSIX 规范的一部分,因此也应该适用于其他 UNIX 变体,请参阅https://pubs.opengroup.org/onlinepubs/9699919799/utilities/bc.html

$ ./add.sh 
Please input numbers to add: 1 2 3
6
Please input numbers to add: 1 2 3 xyz
Invalid input: xyz
Please input numbers to add: 4 5 6 7 8 9
39
Please input numbers to add: 

在此示例运行中,第一个输入行将转换为表达式1+2+3,然后通过管道传输bc以执行计算。第三个输入行被转换为4+5+6+7+8+9并通过管道输送到bc

答案2

Shell 尤其bash不擅长自己进行算术运算。不仅如此,让他们对用户提供的输入进行算术通常构成任意命令执行漏洞

然而,他们擅长的是运行命令,因为这就是他们的用途。

#! /bin/sh -
awk 'BEGIN {printf "Enter numbers, space separated: "}
     {
       sum = 0
       for (i = 1; i <= NF; i++) sum += $i
       print "Sum of those "NF" numbers: "sum
       exit
     }'

在那里,shell(这里使用,sh因为不需要bash)调用awk处理一行输入并添加每个字段的值。awk支持整数和浮点数,并且不存在bash前导 0 的数字被视为八进制的问题,并且不存在 shell 算术 ACE 漏洞

当尝试将字符串解码为数字时,它会尽其所能,在无法识别它时停止(1e4foo例如,又称为)。1e410000whatever0


1 虽然可以如果输入不是来自终端,则不止一个。

相关内容