快排
快排模板
//快排模板
void quick_sort(int q[], int l, int r)
{
if (l >= r) return; // 不能是==, 因为区间可能没有数
int i = l - 1, j = r + 1, x = q[l + r >> 1]; //第12行如果用j,这一行x不能用x=q[r],会导致死循环
while (i < j) // 注意,循环结束i=j 或者 i=j+1 !
{
do i ++ ; while (q[i] < x);
do j -- ; while (q[j] > x);
if (i < j) swap(q[i], q[j]);
}
quick_sort(q, l, j);
quick_sort(q, j + 1, r);
}
题目1
785.快速排序 https://www.acwing.com/problem/content/787/
private static void quick_sort(int[] nums, int l, int r){
if(l >= r) return; //判断递归结束条件 >=
int i=l-1, j =r+1; //给出左右指针的起始位置
int x = nums[l]; // 指定x。(或者用 nums[l+r>>2])
while(i < j){ //循环结束条件<
do i++; while(nums[i] < x); //<
do j--; while(nums[j] > x); //>
if(i < j){ // if <
int tmp = nums[i];
nums[i] = nums[j];
nums[j] = tmp;
}
}
quick_sort(nums, l, j);
quick_sort(nums, j+1, r);
}
题目2
786.第k小的数 https://www.acwing.com/problem/content/788/
import java.util.*;
public class Main{
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
int n = sc.nextInt(), k = sc.nextInt();
int[] nums = new int[n];
for(int i=0; i<n; i++)
nums[i] = sc.nextInt();
System.out.println(qs(nums, 0, n-1, k));
}
private static int qs(int[] nums, int l, int r, int k){
if(l == r) //因为保证第k小的数肯定在lr中间,所以这里可以用l==r
return nums[l];
int i = l-1, j = r+1;
int x = nums[l];
while(i<j){
while(nums[++i] < x);
while(nums[--j] > x);
if(i<j){
int tmp = nums[i];
nums[i] = nums[j];
nums[j] = tmp;
}
}
if(k <= j-l+1)
return qs(nums, l, j, k);
else
return qs(nums, j+1, r, k-(j-l+1));
}
}
归并排序
归并排序模板
int q[N], tmp[N];
void merge_sort(int q[], int l, int r)
{
if (l >= r) return;
int mid = l + r >> 1;
merge_sort(q, l, mid);
merge_sort(q, mid + 1, r);
int k = 0, i = l, j = mid + 1; //k指针 i左半边起点 j右半边起点
while (i <= mid && j <= r) //i<=左半边边界 且 j<=右半边边界
if (q[i] <= q[j]) tmp[k ++ ] = q[i ++ ];
else tmp[k ++ ] = q[j ++ ];
while (i <= mid) tmp[k ++ ] = q[i ++ ];
while (j <= r) tmp[k ++ ] = q[j ++ ];
for (i = l, j = 0; i <= r; i ++, j ++ ) q[i] = tmp[j];
}
题目1
import java.util.*;
public class Main{
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
int n = sc.nextInt();
int[] nums = new int[n];
int[] tmp = new int[n];
for(int i=0; i<n; i++)
nums[i] = sc.nextInt();
merge_sort(nums,tmp, 0, n-1);
for(int i=0; i<n; i++)
System.out.print(nums[i]+" ");
}
private static void merge_sort(int[] nums, int[] tmp, int l, int r){
if(l >= r) return;
int mid = l+r >> 1;
merge_sort(nums,tmp, l, mid);
merge_sort(nums,tmp, mid+1, r);
int i = l, j=mid+1, k=0;
while(i<=mid && j<=r){
if(nums[i] <= nums[j])
tmp[k++] = nums[i++];
else tmp[k++] = nums[j++];
}
while(i<=mid) tmp[k++] = nums[i++];
while(j<=r) tmp[k++] = nums[j++];
for(i=l, j=0; i<=r; i++, j++) nums[i] = tmp[j];
}
}
题目2
import java.util.*;
public class Main{
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
int n = sc.nextInt();
int[] nums = new int[n];
int[] tmp = new int[n];
for(int i=0; i<n; i++)
nums[i] = sc.nextInt();
System.out.println(merge_sort(nums, tmp, 0, n-1));
}
private static long merge_sort(int[] nums, int[] tmp, int l, int r){
if(l >= r) return 0; //可以是==
int mid = l+r >>1;
long res = 0;
res += merge_sort(nums, tmp, l, mid);
res += merge_sort(nums, tmp, mid+1, r);
int i=l, j=mid+1, k=0;
while(i<=mid && j<=r){
if(nums[i] <= nums[j]) tmp[k++] = nums[i++];
else{
tmp[k++] = nums[j++];
res += mid-i+1;
}
}
while(i<=mid) tmp[k++] = nums[i++];
while(j<=r) tmp[k++] = nums[j++];
for(i=l, j=0; i<=r; i++, j++) nums[i] = tmp[j];
return res;
}
}