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

如何在Rust中对浮点型向量(Vec<f64>)进行排序?

Rust中浮点数Vec排序的解决方案

问题出在Vec::sort()方法要求元素实现Ord trait,但f64(以及f32)并没有实现这个 trait——因为浮点数包含NaN(非数字)值,而NaN无法和任何值(包括自身)形成有效的全序比较关系,因此Rust标准库没有为浮点数实现Ord,仅实现了支持部分比较的PartialOrd。

下面是几种可行的解决方式:

1. 用sort_by结合partial_cmp(标准库方案,处理NaN)

通过sort_by自定义比较逻辑,利用PartialOrd::partial_cmp方法处理浮点数比较,同时显式定义NaN的排序位置:

fn main() {
    let mut nums: Vec<f64> = vec![0.53, 3.18, 4.783, 9.0, -1.2, 0.0, f64::NAN];
    // 将NaN排在所有有效数字之后
    nums.sort_by(|a, b| a.partial_cmp(b).unwrap_or(std::cmp::Ordering::Greater));
    println!("{:?}", nums);
    // 输出: [-1.2, 0.0, 0.53, 3.18, 4.783, 9.0, NaN]
}

如果需要把NaN排在最前面,只需把Ordering::Greater换成Ordering::Less即可。

2. 确定无NaN时直接unwrap(简化版标准库方案)

如果你能保证待排序的浮点数中绝对不存在NaN,可以直接对partial_cmp的结果unwrap,代码更简洁,但如果出现NaN会直接panic:

fn main() {
    let mut nums: Vec<f64> = vec![0.53, 3.18, 4.783, 9.0, -1.2, 0.0];
    nums.sort_by(|a, b| a.partial_cmp(b).unwrap());
    println!("{:?}", nums);
    // 输出: [-1.2, 0.0, 0.53, 3.18, 4.783, 9.0]
}

3. 使用第三方库简化排序(可选)

如果不想手动处理NaN逻辑,可以引入ordered-float crate,它提供了OrderedFloat包装类型,内部实现了Ord trait,默认将NaN排在末尾:

首先在Cargo.toml中添加依赖:

[dependencies]
ordered-float = "3.0"

然后编写代码:

use ordered_float::OrderedFloat;

fn main() {
    let mut nums: Vec<OrderedFloat<f64>> = vec![0.53, 3.18, 4.783, 9.0, -1.2, 0.0, f64::NAN]
        .into_iter()
        .map(OrderedFloat)
        .collect();
    nums.sort();
    println!("{:?}", nums);
    // 输出: [OrderedFloat(-1.2), OrderedFloat(0.0), OrderedFloat(0.53), OrderedFloat(3.18), OrderedFloat(4.783), OrderedFloat(9.0), OrderedFloat(NaN)]
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.15 09:07:19