根号n段合并排序算法(详细注释)-Rust语言编写
题目:n\sqrt{n}n段合并排序算法:将数组a[0,n−1]a[0,n-1]a[0,n−1]划分为⌊n⌋⌊\sqrt{n}⌋⌊n⌋个子数组,每个子数组有O(n)O(\sqrt{n})O(n)个元素。然后递归地对分割后的子数组进行排序,最后将所得到的⌊n⌋⌊\sqrt{n}⌋⌊n⌋个排好序的子数组合并排序。解法:use rand::prelude::*;fn square_merge_s
·
题目:
n\sqrt{n}n段合并排序算法:
将数组a[0,n−1]a[0,n-1]a[0,n−1]划分为⌊n⌋⌊\sqrt{n}⌋⌊n⌋个子数组,每个子数组有O(n)O(\sqrt{n})O(n)个元素。然后递归地对分割后的子数组进行排序,最后将所得到的⌊n⌋⌊\sqrt{n}⌋⌊n⌋个排好序的子数组合并排序。
解法:
use rand::prelude::*;
fn square_merge_sort(a: &mut Vec<usize>, start: usize, end: usize) {
let num = ((end - start + 1) as f64).sqrt() as usize;
if num > 1 {
// 前 num - 1 个子数组,数组中元素个数为 num
for i in 0..num - 1 {
square_merge_sort(a, start + i * num, start + (i + 1) * num - 1);
}
// 第 num 个子数组,数组中元素个数可能大于 num
square_merge_sort(a, start + (num - 1) * num, end);
// 进行合并
merge(a, start, end, num);
} else {
// 当 num 为 1 时进行直接排序,即子数组元素个数为 1、2、3 的情况
sort_num_equal_1(a, start, end);
}
}
fn sort_num_equal_1(a: &mut Vec<usize>, start: usize, end: usize) {
let num = end - start + 1;
// 当个数为 1 时直接返回
if num == 1 {
return;
}
// 当个数为 2 时的处理
if a[start] > a[start + 1] {
a.swap(start, start + 1);
}
if num == 3 {
if a[start] > a[start + 2] {
a.swap(start, start + 2);
}
if a[start + 1] > a[start + 2] {
a.swap(start + 1, start + 2);
}
}
}
fn merge(a: &mut Vec<usize>, start: usize, end: usize, num: usize) {
// 新建一个辅助数组
let mut tmp: Vec<usize> = Vec::new();
// 记录每一个子数组当前的索引位置,用于判断子数组是否添加完成
let mut part_index: Vec<usize> = Vec::new();
for _ in 0..num {
part_index.push(0);
}
for _ in 0..end - start + 1 {
let mut min = usize::MAX;
let mut index: usize = 0;
for i in 0..num {
// 如果子数组已经全部添加,则跳过这个子数组,直接遍历下一个子数组,这边要分是前 num 个子数组还是第 num 个子数组两种情况(因为第 num 个子数组个数不一定是 num )
if (i != num - 1 && part_index[i] == num) || (i == num - 1 && part_index[i] == end - start + 1 - (num - 1) * num) {
continue;
}
// 寻找各子数组中的最小值,并做标记是哪一个子数组
if min > a[start + i * (num) + part_index[i]] {
min = a[start + i * (num) + part_index[i]];
index = i;
}
}
// 当前有最小值的子数组索引加 1,表示当前的值已经作为最小值添加过
part_index[index] = part_index[index] + 1;
tmp.push(min);
}
// 修改原数组
for i in 0..end - start + 1 {
a[start + i] = tmp[i];
}
}
fn main() {
// 1、创建一个数组
let mut a: Vec<usize> = Vec::new();
// 2、在数据中生成 50个 0~100 的随机数
let mut rng = rand::thread_rng();
for _ in 0..50 {
a.push(rng.gen_range(0..101));
}
// 3、打印生成的原数组
for (_, num) in a.iter().enumerate() {
print!("{} ", num);
}
// 4、进行排序
let length = a.len();
square_merge_sort(&mut a, 0, length - 1);
// 5、打印排序后的数组
println!("");
for (_, num) in a.iter().enumerate() {
print!("{} ", num);
}
}

魔乐社区(Modelers.cn) 是一个中立、公益的人工智能社区,提供人工智能工具、模型、数据的托管、展示与应用协同服务,为人工智能开发及爱好者搭建开放的学习交流平台。社区通过理事会方式运作,由全产业链共同建设、共同运营、共同享有,推动国产AI生态繁荣发展。
更多推荐
所有评论(0)