alltools.one
Tools
2025-06-18
7 min
alltools.one Team
Unit ConversionMeasurementMetricImperialBest Practices

損失數百萬的單位換算錯誤

單位換算看起來微不足道,直到出了問題。一個小數點放錯、搞混了度量系統,或是時區算錯,後果可能從小 Bug 到災難性的事故。這些真實案例說明了為什麼謹慎處理單位至關重要。

著名的單位換算災難

火星氣候軌道器(1999 年)— 3.276 億美元

NASA 的火星氣候軌道器在火星大氣層中解體,因為一個團隊使用英制單位(磅力·秒),而另一個團隊預期的是公制單位(牛頓·秒)。導航軟體因此錯誤計算推力,使太空船進入軌道時低了 170 公里。

教訓:在介面和文件中務必明確標示單位,永遠不要假設。

Gimli 滑翔機(1983 年)— 險些釀災

一架加拿大航空波音 767 在飛行途中燃油耗盡,因為地面人員將燃油計算單位搞混——用了磅而非公斤。飛機需要 22,300 公斤的燃油,但只加了 22,300 磅(約 10,100 公斤)——不到所需的一半。

飛行員最終將這架失去動力的飛機滑翔降落在曼尼托巴省 Gimli 的一個前空軍基地。

哥倫布與里格

克里斯多福·哥倫布嚴重低估了到亞洲的距離,部分原因是他混淆了阿拉伯里(約 1.8 公里)和較短的羅馬里(約 1.5 公里)。他計算到日本的距離約為 3,700 公里——實際距離超過 19,000 公里。

開發者常犯的錯誤

1. 位元組 vs. 位元

網路速度以位元每秒(Mbps)為單位,而儲存容量以位元組(MB)為單位。100 Mbps 的連線每秒傳輸約 12.5 MB。

100 Mbps ÷ 8 = 12.5 MB/s

許多使用者混淆這兩個單位,不明白為什麼他們的「100 Mbps」連線下載檔案時似乎很慢。

2. Kilobyte:1000 vs. 1024

存在兩套競爭的標準:

前綴十進位(SI)二進位(IEC)
K1,000 位元組 (kB)1,024 位元組 (KiB)
M1,000,000 位元組 (MB)1,048,576 位元組 (MiB)
G1,000,000,000 位元組 (GB)1,073,741,824 位元組 (GiB)

你的「500 GB」硬碟有 500,000,000,000 位元組,也就是 465.66 GiB——這就是為什麼作業系統顯示的容量比標示的少。

3. 溫度換算

攝氏轉華氏的公式是常見的 Bug 來源:

°F = (°C × 9/5) + 32
°C = (°F - 32) × 5/9

某些語言中的整數除法可能導致錯誤:如果兩個運算元都是整數,9/5 可能等於 1 而非 1.8

4. 時區偏移

並非所有時區都是以整數小時為 UTC 偏移:

  • 印度:UTC+5:30
  • 尼泊爾:UTC+5:45
  • 查塔姆群島:UTC+12:45

假設所有時區都是整數小時偏移,會導致數百萬使用者的應用程式出錯。

5. 貨幣精度

金融計算必須使用精確的十進位運算,而非浮點數:

// WRONG
0.1 + 0.2 = 0.30000000000000004

// RIGHT - use integer cents
const total = 10 + 20; // 30 cents
const display = (total / 100).toFixed(2); // "0.30"

使用我們的單位換算器安全地在各單位之間轉換。

開發者最佳實踐

1. 以標準單位儲存

在內部使用每個維度的一個標準單位:

  • 長度:公尺
  • 重量:公斤(或公克)
  • 溫度:克耳文或攝氏
  • 時間:秒(或 Unix 時間戳)
  • 貨幣:最小面額(分)

只在展示層轉換為顯示單位。

2. 明確標示單位

# BAD - ambiguous
distance = 5000
timeout = 30

# GOOD - clear
distance_meters = 5000
timeout_seconds = 30

# BETTER - type safety
from dataclasses import dataclass

@dataclass
class Distance:
    meters: float
    
    @property
    def kilometers(self):
        return self.meters / 1000
    
    @property
    def miles(self):
        return self.meters / 1609.344

3. 在邊界處驗證

從外部來源(API、使用者輸入、檔案)接收單位值時,立即驗證:

def process_temperature(value: float, unit: str) -> float:
    if unit == "celsius":
        return value
    elif unit == "fahrenheit":
        return (value - 32) * 5 / 9
    elif unit == "kelvin":
        return value - 273.15
    else:
        raise ValueError(f"Unknown temperature unit: {unit}")

4. 使用函式庫

對於複雜的換算,使用成熟的函式庫而非手動實作:

  • Pythonpint(具有單位的物理量)
  • JavaScriptconvert-units
  • Javajavax.measure(JSR-385)

常見問題

美國為什麼還在用英制單位?

1975 年的美國公制換算法案將公制採用定為自願而非強制。產業抵制、更換設備的成本,以及公眾對英制單位的熟悉拖慢了採用進程。如今,科學、醫療和軍事使用公制,而日常測量仍使用英制。目前未正式採用公制的國家只有緬甸和賴比瑞亞。

如何在多語系應用程式中處理單位換算?

在內部以標準單位儲存數值。在展示層檢查使用者的語系或偏好設定來決定顯示單位。某些語系有明確的慣例(歐洲用公制、美國用英制),但務必允許使用者覆蓋預設設定。對於溫度,部分地區(美國)預設使用華氏,而世界大部分地區使用攝氏。

相關資源

Published on 2025-06-18
Unit Conversion Mistakes That Cost Millions | alltools.one