use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Copy, PartialEq, Serialize, Deserialize)]
pub struct 缺口 {
pub 高: f64,
pub 低: f64,
}
impl 缺口 {
pub fn new(高: f64, 低: f64) -> Self {
assert!(高 > 低, "缺口高必须大于低: 高={高}, 低={低}");
Self { 高, 低 }
}
pub fn 居中截取区间(起点: f64, 终点: f64, 比例: f64) -> Option<Self> {
let (起点, 终点) = if 起点 <= 终点 {
(起点, 终点)
} else {
(终点, 起点)
};
let 总长 = 终点 - 起点;
let 偏移 = 总长 * 比例;
let 中心 = (起点 + 终点) / 2.0;
let 下界 = 中心 - 偏移;
let 上界 = 中心 + 偏移;
if 下界 > 终点 || 上界 < 起点 {
return None;
}
let 下界 = 下界.max(起点);
let 上界 = 上界.min(终点);
Some(Self::new(上界.max(下界), 上界.min(下界)))
}
}
impl std::fmt::Display for 缺口 {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(
f,
"缺口区间<{} <=> {}>",
crate::utils::format_f64_g(self.低),
crate::utils::format_f64_g(self.高)
)
}
}