我试图创建一个简单的计算器使用bash脚本。面临的主要问题是,它不要求任何算术运算的第二个操作数。此外,它不适用于负数作为算术运算的操作数。请看下面的脚本。
#!/bin/bash
# Display user instructions
echo "Welcome to the Simple Calculator"
echo "Instructions:"
echo "Enter operand: Any digit, MR, MC, Clear (C), Off (X)"
echo "Enter operator: +, -, *, /, MS, M+, MC, Clear (C), Off (X)"
echo "------------------------------------------"
# Initialize variables
result=0
memory=0
while true; do
# Start an infinite loop to keep the calculator running
# Prompt for operand
read -p "Enter operand: " input_operand
# Use 'read' to get user input for operand and store it in 'input_operand'
case "$input_operand" in
[0-9]*) operand="$input_operand";;
# If input_operand is a digit, assign it to the 'operand' variable
"MR") operand="$result";;
# If input_operand is "MR", use the previous result as the operand
"MC") memory=0; echo "0 -> M"; continue;;
# If input_operand is "MC", clear the memory and display the message
"C") result=0; echo "results cleared"; continue;;
# If input_operand is "C", clear the result and display the message
"X") echo "Good bye."; exit 0;;
# If input_operand is "X", exit the script with a farewell message
*) echo "Invalid input. Please re-enter operand."; continue;;
# For any other input, display an error message and continue to the next iteration
esac
# Prompt for operator
read -p "Enter operator: " operator
# Use 'read' to get user input for the operator and store it in 'operator'
case "$operator" in
"+") result=$((result + operand));;
# If the operator is "+", perform addition
"-") result=$((result - operand));;
# If the operator is "-", perform subtraction
"*") result=$((result * operand));;
# If the operator is "*", perform multiplication
"/")
if [ "$operand" -eq 0 ]; then
echo "Can't divide by zero. Please re-enter divisor."
continue
else
result=$((result / operand))
fi
# If the operator is "/", handle division with a check for division by zero
;;
"MS") memory="$result"; echo "$result -> M";;
# If the operator is "MS", store the result in memory and display a message
"M+") memory=$((memory + result));;
# If the operator is "M+", add the result to the memory
"MR") operand="$memory";;
# If the operator is "MR", use the value from memory as the operand
"MC") memory=0; echo "0 -> M";;
# If the operator is "MC", clear the memory and display a message
"C") result=0; echo "results cleared";;
# If the operator is "C", clear the result and display a message
"X") echo "Good bye."; exit 0;;
# If the operator is "X", exit the script with a farewell message
*) echo "Invalid operator. Please re-enter operator."; continue;;
# For any other input, display an error message and continue to the next iteration
esac
echo "$result $operator $operand = $result"
# Display the result of the current operation
done
以下是错误输出的示例:
Welcome to the Simple Calculator
Instructions:
Enter operand: Any digit, MR, MC, Clear (C), Off (X)
Enter operator: +, -, *, /, MS, M+, MC, Clear (C), Off (X)
------------------------------------------
Enter operand: 3
Enter operator: *
0 * 3 = 0
Enter operand: 4
Enter operator: +
4 + 4 = 4
Enter operand:
以下是正确预期输出的示例序列:
$ ./calc
[ *** User instructions displayed *** ]
Enter operand: 3
Enter operator: +
Enter operand: 4
3 + 4 = 7
Enter operator: -
Enter operand: 12
7 - 12 = -5
Enter operator: MS
-5 -> M
Enter operator: *
Enter operand: 3
-5 * 3 = -15
Enter operator: C
results cleared
Enter operand: MR
M -> -5
Enter operator: *
Enter operand: MR
M -> -5
-5 * -5 = 25
Enter operator: M+
25 + -5 = 20 -> M
Enter operator: /
Enter operand: 0
Can't divide by zero. Please re-enter divisor.
Enter operand: 0
Can't divide by zero. Please re-enter divisor.
Enter operand: -6
25 / -6 = -4
Enter operator: +
Enter operand: C
results cleared
Enter operand: -9
Enter operator: k
Sorry, k, is not a valid operator. Please re-enter operator.
Enter operator: MC
0 -> M
Enter operator: +
Enter operand: 3
-9 + 3 = -6
Enter operator: X
Good bye.
更新1:我已经根据其中一条评论中提供的高级伪代码设计修改了原始脚本。但是,它仍然显示不正确的输出。
#!/bin/bash
# Display user instructions
echo "Welcome to the Simple Calculator"
echo "Instructions:"
echo "Enter operand: Any digit, MR, MC, Clear (C), Off (X)"
echo "Enter operator: +, -, *, /, MS, M+, MC, Clear (C), Off (X)"
echo "------------------------------------------"
# Initialize variables
result=0
memory=0
# Function to get an operand
get_operand() {
read -p "Enter operand: " input_operand
case "$input_operand" in
[0-9]*) operand="$input_operand";;
"MR") operand="$result";;
"MC") memory=0; echo "0 -> M";;
"C") result=0; echo "results cleared";;
"X") echo "Good bye."; exit 0;;
*) echo "Invalid input. Please re-enter operand."
get_operand;;
esac
}
# Function to get an operator
get_operator() {
read -p "Enter operator: " operator
case "$operator" in
"+"|"-"|"*"|"/") ;;
"MS") memory="$result"; echo "$result -> M";;
"M+") memory=$((memory + result));;
"MR") operand="$memory";;
"MC") memory=0; echo "0 -> M";;
"C") result=0; echo "results cleared";;
"X") echo "Good bye."; exit 0;;
*) echo "Invalid operator. Please re-enter operator."
get_operator;;
esac
}
# Initial operand entry
get_operand
while true; do
get_operator
if [ "$operator" == "MS" ] || [ "$operator" == "M+" ]; then
continue
fi
get_operand
case "$operator" in
"+") result=$((result + operand));;
"-") result=$((result - operand));;
"*") result=$((result * operand));;
"/")
if [ "$operand" -eq 0 ]; then
echo "Can't divide by zero. Please re-enter divisor."
get_operand
else
result=$((result / operand))
fi
;;
esac
echo "$result $operator $operand = $result"
done
以下是错误的输出:
Welcome to the Simple Calculator
Instructions:
Enter operand: Any digit, MR, MC, Clear (C), Off (X)
Enter operator: +, -, *, /, MS, M+, MC, Clear (C), Off (X)
------------------------------------------
Enter operand: 3
Enter operator: +
Enter operand: 4
4 + 4 = 4
Enter operator:
更新2:我已经根据@Ed Morton在评论中提供的方法添加了其余的功能。以下是完整的脚本:
#!/usr/bin/env bash
# Initialize variables
result=0
memory=0
# Function to get an operand
get_operand() {
local input
while true; do
read -p "Enter operand: " input
case "$input" in
[0-9]*) echo "$input"; break;;
"MR") echo "$result"; break;;
"MC") memory=0; echo "0 -> M";;
"C") result=0; echo "results cleared";;
"X") echo "Good bye."; exit 0;;
*) echo "Invalid input. Please re-enter operand."
esac
done
}
# Function to get an operator
get_operator() {
local input
while true; do
read -p "Enter operator: " input
case "$input" in
"+"|"-"|"*"|"/") echo "$input"; break;;
"MS") memory="$result"; echo "$result -> M";;
"M+") memory=$((memory + result));;
"MR") echo "$memory"; break;;
"MC") memory=0; echo "0 -> M";;
"C") result=0; echo "results cleared";;
"X") echo "Good bye."; exit 0;;
*) echo "Invalid operator. Please re-enter operator."
esac
done
}
# Initial operand entry
result=$(get_operand)
while true; do
operator=$(get_operator)
operand=$(get_operand)
prev_result="$result"
case "$operator" in
"+") result=$((result + operand));;
"-") result=$((result - operand));;
"*") result=$((result * operand));;
"/")
if [ "$operand" -eq 0 ]; then
echo "Can't divide by zero. Please re-enter divisor."
continue
fi
result=$((result / operand))
;;
esac
echo "$prev_result $operator $operand = $result"
done
但现在它显示的是不正确的运算结果,而不是算术运算。显示以下错误输出。
Enter operand: 3
Enter operator: +
Enter operand: 4
3 + 4 = 7
Enter operator: -
Enter operand: 12
7 - 12 = -5
Enter operator: MS
Enter operator: *
Enter operand: 3
-5 -5 -> M
* 3 = -5
Enter operator: C
Enter operator: C
Enter operator: MR
Enter operand:
预期根据上述共享示例序列(非穷举测试)获得正确的预期输出。
2条答案
按热度按时间aiazj4mn1#
当前的问题似乎与一些不完整的逻辑有关,即何时请求新的
operator
和新的operand
。在不尝试查看
operand
+operator
的所有可能组合的情况下,使用OP的“正确预期输出”作为模板,在我看来,一般流程如下所示:高级伪代码设计:
显然,用
read / case
块替换get_*
和process_*
调用(或者可能推入一对函数,使while true
循环更清晰?).dffbzjpn2#
我剥离了你的代码,只是让
+
工作。试试这个:你会看到它的工作原理:
现在将您的其他功能添加到它上面。
FWIW为了简单和清晰,我会在
get_...
函数中使用循环而不是递归,例如: