1. 归并排序算法设计:
(1) 将待排序数组分解为各含 n/2 个元素的子数组;
(2) 将两个子数组排序好;
(3)将排序好的子数组合并,得到最后的结果.
2. 归并排序的流程:
3. 归并排序的并操作流程:
4. 动态展示:
5. 源码实现:
package edu.xalead.Test;
import java.util.List;
public class Collections {
public static void sort(List list){
int l =0;
int r = list.size()-1;
//归并
devide(list,l,r);
}
/**
* 归==>分治
*/
private static void devide(List list,int left,int right){
//递归
int mid = (left + right)/2;
if(left<right) {
devide(list, left, mid);
devide(list, mid + 1, right);
//并
merge(list,left,mid,mid+1,right);
}
}
private static void merge(List list, int left, int mid, int i, int right) {
Object[] temp = new Object[list.size()];
int index = left; // 起始索引从自己开始
int ls = left, le = mid; // leftstart leftend
int rs = i,re = right;
//至少把一边的数组按顺序放入临时数组
while(ls <= le && rs<=re){
Comparable o1 = (Comparable) list.get(ls);
Comparable o2 = (Comparable) list.get(rs);
if(o1.compareTo(o2) == -1){ // o1<o2 retrun -1;
temp[index] = o1;
ls++;
}else{
temp[index] = o2; // o1>=o2
rs++;
}
index++;
}
//判断左边是否有剩余元素
if(ls <=le){
for(int j = ls;j<=le;j++){
temp[index++] = list.get(j);
}
}
//判断右边是否有剩余元素
if(rs <= re){
for(int j = rs;j<=re;j++){
temp[index++] = list.get(j);
}
}
for(int j = left ;j<= right; j++){
list.set(j,temp[j]);
}
}
}
package edu.xalead.Test;
import edu.xalead.Iterator;
import edu.xalead.collection.Student;
import org.junit.Test;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
public class testCollection {
@Test
public void test1() {
List<Student> list = new ArrayList<>();
java.util.Collections.sort(list,
(o1, o2) -> {
if (o1 instanceof Student && o2 instanceof Student) {
Student s1 = (Student) o1;
Student s2 = (Student) o2;
if (s1.getId() > s2.getId()) return 1;
if (s1.getId() < s2.getId()) return -1;
return 0;
}
throw new RuntimeException("类型不匹配无法比较");
});
}
@Test
public void test2() {
List<Integer> s = new ArrayList<>();
s.add(12);
s.add(234);
s.add(4354);
s.add(46546);
s.add(0);
s.add(-124);
//反转
System.out.println(s);
Collections.reverse(s);
System.out.println(s);
//从大到小排序
Collections.sort(s);
System.out.println(s);
// 打乱
Collections.shuffle(s);
System.out.println(s);
// 交换索引i和j的索引位置
Collections.swap(s, 4, 1);
System.out.println(s);
// 旋转
Collections.rotate(s, 3);
System.out.println(s);
// Collections.binarySearch();
}
@Test
public void test3() {
List s = new ArrayList();
s.add(new Student(324324, "HAHA"));
s.add(new Student(143543, "DAHA"));
s.add(new Student(323545, "JAHA"));
s.add(new Student(423545, "WAHA"));
System.out.println("排序前: \n " + s);
edu.xalead.Test.Collections.sort(s);
System.out.println("排序后: \n" + s);
}
@Test
public void test4(){
List s = new ArrayList();
s.add(5);
s.add(4);
s.add(7);
s.add(9);
s.add(3);
s.add(2);
s.add(1);
System.out.println("排序前:\n" + s );
edu.xalead.Test.Collections.sort(s);
System.out.println("排序后: \n" + s);
}
}
package edu.xalead.collection;
public class Student implements Comparable{
private int id;
private String name;
public Student(int id,String name){
this.id = id;
this.name = name;
}
@Override
public String toString() {
return "Student{" +
"id=" + id +
", name='" + name + '\'' +
'}' + "\n";
}
public Student(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
@Override
public int compareTo(Object o) {
if(o instanceof Student){
Student s = (Student) o;
if(this.id > s.id) return 1;
if(this.id < s.id) return -1;
return 0;
}
throw new RuntimeException("类型不匹配无法比较!");
}
}
5. 测试结果:
用Comparable接口实现对数组的排布
用Comparable接口实现对Student类的排布