#include "timsort.h"
#include <stdlib.h>
#include <string.h>
// 将两个长度分别为l1, l2的已排序数组p1, p2合并为一个
// 已排序的目标数组。
void merge(int target[], int p1[], int l1, int p2[], int l2);
void integer_timsort(int array[], int size){
if(size <= 1) return;
int partition = size/2;
integer_timsort(array, partition);
integer_timsort(array + partition, size - partition);
merge(array, array, partition, array + partition, size - partition);
}
void merge(int target[], int p1[], int l1, int p2[], int l2){
int *merge_to = malloc(sizeof(int) * (l1 + l2));
// 当前扫描两数组的位置
int i1, i2;
i1 = i2 = 0;
// 在合并过程中存放下一个元素的位置
int *next_merge_element = merge_to;
// 扫描两数组,将较小的元素写入
// merge_to. 当两数相等时我们选择
// 左边的, 因为我们想保证排序的稳定性
// 当然对于integers这无关紧要,但这种想法是很重要的
while(i1 < l1 && i2 < l2){
if(p1[i1] <= p2[i2]){
*next_merge_element = p1[i1];
i1++;
} else {
*next_merge_element = p2[i2];
i2++;
}
next_merge_element++;
}
// 如果有一个数组没有扫描完,我们直接拷贝剩余的部分
memcpy(next_merge_element, p1 + i1, sizeof(int) * (l1 - i1));
memcpy(next_merge_element, p2 + i2, sizeof(int) * (l2 - i2));
// 现在我们已经将他们合并在了我们的额外的存储空间里了
// 是时候转存到target了
memcpy(target, merge_to, sizeof(int) * (l1 + l2));
free(merge_to);
}
#include "timsort.h"
#include <stdlib.h>
#include <string.h>
// 将两个长度分别为l1, l2的已排序数组p1, p2合并为一个
// 已排序的目标数组。
void merge(int target[], int p1[], int l1, int p2[], int l2);
void integer_timsort(int array[], int size){
if(size <= 1) return;
int partition = size/2;
integer_timsort(array, partition);
integer_timsort(array + partition, size - partition);
merge(array, array, partition, array + partition, size - partition);
}
void merge(int target[], int p1[], int l1, int p2[], int l2){
int *merge_to = malloc(sizeof(int) * (l1 + l2));
// 当前扫描两数组的位置
int i1, i2;
i1 = i2 = 0;
// 在合并过程中存放下一个元素的位置
int *next_merge_element = merge_to;
// 扫描两数组,将较小的元素写入
// merge_to. 当两数相等时我们选择
// 左边的, 因为我们想保证排序的稳定性
// 当然对于integers这无关紧要,但这种想法是很重要的
while(i1 < l1 && i2 < l2){
if(p1[i1] <= p2[i2]){
*next_merge_element = p1[i1];
i1++;
} else {
*next_merge_element = p2[i2];
i2++;
}
next_merge_element++;
}
// 如果有一个数组没有扫描完,我们直接拷贝剩余的部分
memcpy(next_merge_element, p1 + i1, sizeof(int) * (l1 - i1));
memcpy(next_merge_element, p2 + i2, sizeof(int) * (l2 - i2));
// 现在我们已经将他们合并在了我们的额外的存储空间里了
// 是时候转存到target了
memcpy(target, merge_to, sizeof(int) * (l1 + l2));
free(merge_to);
}
void merge(int target[], int p1[], int l1, int p2[], int l2, int storage[]);
void integer_timsort_with_storage(int array[], int size, int storage[]);
void integer_timsort(int array[], int size){
int *storage = malloc(sizeof(int) * size);
integer_timsort_with_storage(array, size, storage);
free(storage);
}
void merge(int target[], int p1[], int l1, int p2[], int l2, int storage[]);
void integer_timsort_with_storage(int array[], int size, int storage[]);
void integer_timsort(int array[], int size){
int *storage = malloc(sizeof(int) * size);
integer_timsort_with_storage(array, size, storage);
free(storage);
}
void insertion_sort(int xs[], int length){
if(length <= 1) return;
int i;
for(i = 1; i < length; i++){
// i之前的数组已经有序了,现在将xs[i]插入到里面
int x = xs[i];
int j = i - 1;
// 将j向前移动直到数组头或者
// something <= x, 并且其右边的所有的元素都已经
// 右移了
while(j >= 0 && xs[j] > x){
xs[j+1], xs[j];
j--;
}
xs[j+1] = x;
}
}
void insertion_sort(int xs[], int length){
if(length <= 1) return;
int i;
for(i = 1; i < length; i++){
// i之前的数组已经有序了,现在将xs[i]插入到里面
int x = xs[i];
int j = i - 1;
// 将j向前移动直到数组头或者
// something <= x, 并且其右边的所有的元素都已经
// 右移了
while(j >= 0 && xs[j] > x){
xs[j+1], xs[j];
j--;
}
xs[j+1] = x;
}
}
void integer_timsort_with_storage(int array[], int size, int storage[]){
if(size <= INSERTION_SORT_SIZE){
insertion_sort(array, size);
return;
}
}
void integer_timsort_with_storage(int array[], int size, int storage[]){
if(size <= INSERTION_SORT_SIZE){
insertion_sort(array, size);
return;
}
}
{5, 6, 7, 8, 9, 10, 1, 2, 3}
{{1}, {2}, {3}, {4}}
{{1, 2}, {3, 4}}
{{1, 2, 3, 4}}
// 我们使用固定的栈大小,这个大小要远远大于任何合理的栈高度
// 当然,我们仍然需要对溢出进行检查
#define STACK_SIZE 1024
typedef struct {
int *index;
int length;
} run;
typedef struct {
int *storage;
// 存储已经得到的分段(runs,原文作者将得到分段叫做run)
run runs[STACK_SIZE];
// 栈顶指针,指向下一个待插入的位置
int stack_height;
// 保持记录我们已经分段到哪里里,这样我们可以知道在哪里开始下一次的分段
// 数组中index < partioned_up_to 是已经分段并存储在栈上的, 而index >= partioned_up_to
// 的元素是还没有存储到栈上的. 当partitioned_up_to == 数组长度的时候所有的元素都在栈上了
int *partitioned_up_to;
int *array;
int length;
} sort_state_struct;
typedef sort_state_struct *sort_state;
// 我们使用固定的栈大小,这个大小要远远大于任何合理的栈高度
// 当然,我们仍然需要对溢出进行检查
#define STACK_SIZE 1024
typedef struct {
int *index;
int length;
} run;
typedef struct {
int *storage;
// 存储已经得到的分段(runs,原文作者将得到分段叫做run)
run runs[STACK_SIZE];
// 栈顶指针,指向下一个待插入的位置
int stack_height;
// 保持记录我们已经分段到哪里里,这样我们可以知道在哪里开始下一次的分段
// 数组中index < partioned_up_to 是已经分段并存储在栈上的, 而index >= partioned_up_to
// 的元素是还没有存储到栈上的. 当partitioned_up_to == 数组长度的时候所有的元素都在栈上了
int *partitioned_up_to;
int *array;
int length;
} sort_state_struct;
typedef sort_state_struct *sort_state;
while(next_partition(&state)){
while(should_collapse(&state)) merge_collapse(&state);
}
while(state.stack_height > 1) merge_collapse(&state);
while(next_partition(&state)){
while(should_collapse(&state)) merge_collapse(&state);
}
while(state.stack_height > 1) merge_collapse(&state);
64, 32, 16, 8, 4, 2, 1
64, 32, 16, 8, 4, 2, 1, 1 64, 32, 16, 8, 4, 2, 2 64, 32, 16, 8, 4, 4 64, 32, 16, 8, 8 64, 32, 16, 16 64, 32, 32 64, 64 128
int should_collapse(sort_state state){
if (state->stack_height <= 2) return 0;
int h = state->stack_height - 1;
int head_length = state->runs[h].length;
int next_length = state->runs[h-1].length;
return 2 * head_length > next_length;
}
int should_collapse(sort_state state){
if (state->stack_height <= 2) return 0;
int h = state->stack_height - 1;
int head_length = state->runs[h].length;
int next_length = state->runs[h-1].length;
return 2 * head_length > next_length;
}
5, 4, 3, 2, 1
{5}
{5}, {4}
{4, 5}
{4, 5}, {3}
{4, 5}, {3}, {2}
{4, 5}, {2, 3}
{2, 3, 4, 5}
{2, 3, 4, 5}, {1}
{1, 2, 3, 4, 5}
if(next_start_index < state->array + state->length){
if(*next_start_index < *start_index){
// We have a decreasing sequence starting here.
while(next_start_index < state->array + state->length){
if(*next_start_index < *(next_start_index - 1)) next_start_index++;
else break;
}
// Now reverse it in place.
reverse(start_index, next_start_index - start_index);
} else {
// We have an increasing sequence starting here.
while(next_start_index < state->array + state->length){
if(*next_start_index >= *(next_start_index - 1)) next_start_index++;
else break;
}
}
}
if(next_start_index < state->array + state->length){
if(*next_start_index < *start_index){
// We have a decreasing sequence starting here.
while(next_start_index < state->array + state->length){
if(*next_start_index < *(next_start_index - 1)) next_start_index++;
else break;
}
// Now reverse it in place.
reverse(start_index, next_start_index - start_index);
} else {
// We have an increasing sequence starting here.
while(next_start_index < state->array + state->length){
if(*next_start_index >= *(next_start_index - 1)) next_start_index++;
else break;
}
}
}
{1, 2, 3, 4, 5, 4, 3, 2, 1}
{1, 2, 3, 4, 5}
{1, 2, 3, 4, 5}, {1, 2, 3, 4}
{1, 1, 2, 2, 3, 3, 4, 4, 5}
if(run_to_add.length < MIN_RUN_SIZE){
boost_run_length(state, &run_to_add);
}
state->partitioned_up_to = start_index + run_to_add.length;
if(run_to_add.length < MIN_RUN_SIZE){
boost_run_length(state, &run_to_add);
}
state->partitioned_up_to = start_index + run_to_add.length;
boot_run_length函数如下:
void boost_run_length(sort_state state, run *run){
// Need to make sure we don't overshoot the end of the array
int length = state->length - (run->index - state->array);
if(length > MIN_RUN_SIZE) length = MIN_RUN_SIZE;
insertion_sort(run->index, length);
run->length = length;
}
void boost_run_length(sort_state state, run *run){
// Need to make sure we don't overshoot the end of the array
int length = state->length - (run->index - state->array);
if(length > MIN_RUN_SIZE) length = MIN_RUN_SIZE;
insertion_sort(run->index, length);
run->length = length;
}
机械节能产品生产企业官网模板...
大气智能家居家具装修装饰类企业通用网站模板...
礼品公司网站模板
宽屏简约大气婚纱摄影影楼模板...
蓝白WAP手机综合医院类整站源码(独立后台)...苏ICP备2024110244号-2 苏公网安备32050702011978号 增值电信业务经营许可证编号:苏B2-20251499 | Copyright 2018 - 2025 源码网商城 (www.ymwmall.com) 版权所有