【quantity】6 温度单位实现(temperature.rs)
一源码
以下代码实现了一个温度单位系统,支持开尔文(Kelvin)和摄氏度(Celsius)之间的转换和运算。
/// Temperature (kelvin) / 温度 (开尔文)
use super::{Quantity, prefix::*};
use crate::unit::Kelvin;
use derive_more::{Add, Sub, AddAssign, SubAssign};/// Generic temperature with SI prefixes / 带SI前缀的通用温度
///
/// # Type Parameters / 类型参数
/// - `V`: Value type (f32, f64, etc.) / 值类型 (如 f32, f64 等)
/// - `P`: SI prefix type (NoPrefix, Kilo, etc.) / SI前缀类型 (无前缀, 千等)
pub type Temperature<V, P = NoPrefix> = Quantity<V, P, Kelvin>;/// Kelvins / 开尔文
///
/// # Type Parameters / 类型参数
/// - `V`: Value type (f32, f64, etc.) / 值类型 (如 f32, f64 等)
pub type Kelvins<V> = Temperature<V, NoPrefix>;/// Celsius temperature / 摄氏温度
///
/// # Type Parameters / 类型参数
/// - `V`: Value type that implements Copy (f32, f64, etc.) / 实现了Copy的值类型 (如 f32, f64 等)
#[derive(Debug, Clone, Copy, PartialEq, Add, Sub, AddAssign, SubAssign)]
pub struct Celsius<V: Copy>(pub V);impl<V: Copy> Celsius<V> {/// Create new Celsius temperature / 创建新的摄氏温度值/// /// # Arguments / 参数/// - `degrees`: Temperature value in Celsius / 摄氏温度值/// /// # Returns / 返回值/// New Celsius instance / 新的摄氏温度实例pub fn new(degrees: V) -> Self {Self(degrees)}/// Extract inner value / 解构获取内部值/// /// # Returns / 返回值/// The contained temperature value / 包含的温度值pub fn into_inner(self) -> V {self.0}
}// Conversion implementations / 转换实现
impl<V: Copy + From<f64> + Into<f64>> From<Celsius<V>> for Kelvins<V> {/// Convert Celsius to Kelvins / 摄氏温度转开尔文温度/// /// Formula: K = °C + 273.15 / 公式: K = °C + 273.15fn from(c: Celsius<V>) -> Self {Kelvins::new(V::from(c.0.into() + 273.15))}
}impl<V: Copy + From<f64> + Into<f64>> From<Kelvins<V>> for Celsius<V> {/// Convert Kelvins to Celsius / 开尔文温度转摄氏温度/// /// Formula: °C = K - 273.15 / 公式: °C = K - 273.15fn from(k: Kelvins<V>) -> Self {Celsius::new(V::from(k.into_inner().into() - 273.15))}
}#[cfg(test)]
mod tests {use super::*;#[test]fn test_celsius_new() {let temp = Celsius::new(23.5);assert_eq!(temp.into_inner(), 23.5);}#[test]fn test_celsius_to_kelvin() {let celsius = Celsius::new(25.0);let kelvin: Kelvins<f64> = celsius.into();assert!((kelvin.into_inner() - 298.15).abs() < f64::EPSILON);}#[test]fn test_kelvin_to_celsius() {let kelvin = Kelvins::new(300.0);let celsius: Celsius<f64> = kelvin.into();assert!((celsius.into_inner() - 26.85).abs() < 1e-10);}#[test]fn test_celsius_addition() {let t1 = Celsius::new(10.0);let t2 = Celsius::new(20.5);let sum = t1 + t2;assert!((sum.into_inner() - 30.5f64).abs() < f64::EPSILON);}#[test]fn test_celsius_subtraction() {let t1 = Celsius::new(30.0);let t2 = Celsius::new(15.5);let diff = t1 - t2;assert!((diff.into_inner() - 14.5f64).abs() < f64::EPSILON);}#[test]fn test_conversion_roundtrip() {let original = Celsius::new(100.0);let kelvin: Kelvins<f64> = original.into();let celsius: Celsius<f64> = kelvin.into();assert!((celsius.into_inner() - 100.0).abs() < 1e-10);}#[test]fn test_zero_kelvin() {let kelvin = Kelvins::new(0.0);let celsius: Celsius<f64> = kelvin.into();assert!((celsius.into_inner() - (-273.15)).abs() < f64::EPSILON);}
}
二、主要组成部分
1. 温度类型定义
/// 带SI前缀的通用温度
pub type Temperature<V, P = NoPrefix> = Quantity<V, P, Kelvin>;/// 开尔文温度
pub type Kelvins<V> = Temperature<V, NoPrefix>;
-
Temperature 是一个泛型类型,表示带SI前缀的温度值
-
Kelvins 是特化的Temperature类型,表示无前缀的开尔文温度
2. 摄氏度类型
#[derive(Debug, Clone, Copy, PartialEq, Add, Sub, AddAssign, SubAssign)]
pub struct Celsius<V: Copy>(pub V);
-
Celsius 结构体表示摄氏温度
-
派生了许多trait使其支持调试、克隆、拷贝、比较和基本运算
3. 转换实现
// 摄氏转开尔文
impl<V: Copy + From<f64> + Into<f64>> From<Celsius<V>> for Kelvins<V> {fn from(c: Celsius<V>) -> Self {Kelvins::new(V::from(c.0.into() + 273.15))}
}// 开尔文转摄氏
impl<V: Copy + From<f64> + Into<f64>> From<Kelvins<V>> for Celsius<V> {fn from(k: Kelvins<V>) -> Self {Celsius::new(V::from(k.into_inner().into() - 273.15))}
}
实现了两种温度单位之间的双向转换:
-
摄氏转开尔文:K = °C + 273.15
-
开尔文转摄氏:°C = K - 273.15
4. 测试用例
包含了对以下功能的测试:
-
摄氏温度的创建和值获取
-
摄氏与开尔文之间的转换
-
摄氏温度的加减运算
-
转换的往返测试(确保转换不会丢失精度)
-
绝对零度(0K)的特殊情况测试
设计特点
-
类型安全:使用泛型确保不同类型温度不能直接混合运算
-
单位明确:通过类型系统区分开尔文和摄氏温度
-
可扩展性:支持添加更多温度单位(如华氏度)
-
运算支持:通过derive宏自动实现加减运算
-
精确转换:确保温度单位转换的准确性
这个实现适用于需要精确温度计算和单位转换的科学和工程应用。