You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何精简输出结果为英文单词的Bash计算器脚本?

Refactoring Your Bash Calculator to Avoid Endless if/elif Blocks

Absolutely! Those messy if/elif chains are exactly the kind of thing we can clean up with arrays—way more maintainable, especially when you need to extend support up to 30. Let’s break down how to refactor your script properly:

First, let’s fix a couple of small syntax bugs in your original code:

  • The shebang line should be #!/bin/bash (you missed the slash before bin)
  • Conditions like [ $ans == 7] are missing a space before the closing bracket, which would throw errors

Now, the core fix: replace all those if/elif checks with a numeric array that maps each number (0-30) directly to its English word equivalent. This makes extending to 30 trivial, and the code way cleaner.

Here’s the refactored script:

#!/bin/bash

# Array mapping numbers 0-30 to their English word counterparts
declare -a num_words=(
    [0]="zero" [1]="one" [2]="two" [3]="three" [4]="four"
    [5]="five" [6]="six" [7]="seven" [8]="eight" [9]="nine"
    [10]="ten" [11]="eleven" [12]="twelve" [13]="thirteen" [14]="fourteen"
    [15]="fifteen" [16]="sixteen" [17]="seventeen" [18]="eighteen" [19]="nineteen"
    [20]="twenty" [21]="twenty-one" [22]="twenty-two" [23]="twenty-three" [24]="twenty-four"
    [25]="twenty-five" [26]="twenty-six" [27]="twenty-seven" [28]="twenty-eight" [29]="twenty-nine"
    [30]="thirty"
)

while true; do
    # Get input numbers with basic validation (optional but helpful)
    read -p "First number: " n1
    if ! [[ $n1 =~ ^[0-9]+$ ]]; then
        echo "Please enter a valid whole number."
        continue
    fi

    read -p "Second number: " n2
    if ! [[ $n2 =~ ^[0-9]+$ ]]; then
        echo "Please enter a valid whole number."
        continue
    fi

    # Select operation
    PS3="What's the operation? "
    select ans in add subtract multiply divide; do
        case $ans in
            add) op='+' ; break ;;
            subtract) op='-' ; break ;;
            multiply) op='*' ; break ;;
            divide) op='/' ; break ;;
            *) echo "Invalid response, please try again." ;;
        esac
    done

    # Calculate result and convert to integer (handles bc's floating-point output)
    result=$(echo "$n1 $op $n2" | bc -l)
    int_result=$(printf "%.0f" "$result") # Round to nearest whole number

    # Check if result is within our supported range and output
    if [[ $int_result -ge 0 && $int_result -le 30 ]]; then
        printf "%s %s %s = %s\n" "$n1" "$op" "$n2" "${num_words[$int_result]}"
    else
        echo "Oops! Result ($int_result) is outside the 0-30 range we support."
    fi
done

Key Improvements:

  • No more if/elif hell: The array lets us look up the word in one line with ${num_words[$int_result]}
  • Handles floating-point results: bc -l outputs decimals (e.g., 1.000000), so we round to an integer to match our array indices
  • Input validation: Added checks to ensure users enter valid whole numbers (prevents errors from non-numeric input)
  • Range checking: Tells users if their result is outside the 0-30 range instead of silently failing
  • Easy to extend: To support numbers beyond 30, just add more entries to the num_words array

内容的提问来源于stack exchange,提问作者melkor787

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.27 06:48:05