今天隨手了一段代碼關於通過treeSet實現自動排序的功能,自己折騰了好久。
始終是存在這一些疑惑,後來和同學的交流和調試可以解釋自動排序的基本原理:
通過可以通過兩種方式實現自動排序:
一種:
package xyxysjxy.io; import java.io.BufferedReader; import java.io.BufferedWriter; import java.io.FileWriter; import java.io.IOException; import java.io.InputStreamReader; import java.util.Comparator; import java.util.Iterator; import java.util.Set; import java.util.TreeSet; public class StudentInfoImport { public static void main(String[] args) throws IOException { BufferedWriter bw = new BufferedWriter( new FileWriter("f:\\student.txt")); Setss = StudentTools.getStudent(); Iterator is = ss.iterator(); while (is.hasNext()) { Student student = (Student) is.next(); bw.write(student.toString()); bw.newLine(); bw.flush(); } bw.close(); } } class Student{ private String name; private int cn; private int math; private int en; private int sum; public String getName() { return name; } public void setName(String name) { this.name = name; } public int getCn() { return cn; } public void setCn(int cn) { this.cn = cn; } public int getMath() { return math; } public void setMath(int math) { this.math = math; } public int getEn() { return en; } public void setEn(int en) { this.en = en; } public int getSum() { return sum; } public void setSum(int sum) { this.sum = sum; } public Student(String name, int... is) { this.name = name; this.cn = is[0]; this.math = is[1]; this.en = is[2]; this.sum = cn + math + en; } @Override public String toString() { return "【name=" + name + "\tcn=" + cn + "\tmath=" + math + "\ten=" + en + "\tsum=" + sum + "】"; } @Override public boolean equals(Object obj) { if (!(obj instanceof Student)) throw new ClassCastException("不能強制的轉換"); Student s = (Student) obj; return s.name.equals(this.name) && s.sum == s.sum; } @Override public int hashCode() { return sum * 78 + name.hashCode(); } } class StudentTools { static Comparator com = new Comparator () { @Override public int compare(Student o1, Student o2) { int sum = new Integer(o1.getSum()).compareTo(new Integer(o2.getSum())); if (sum == 0) return o1.getName().compareTo(o2.getName()); return sum; } }; public static Set getStudent() throws IOException { return getStudent(com); } public static Set getStudent(Comparator com) throws IOException { Set studentSet = null; if (com == null) studentSet = new TreeSet (); else studentSet = new TreeSet (com); BufferedReader br = new BufferedReader(new InputStreamReader(System.in)); String len = ""; while ((len = br.readLine()) != null) { if (len.equals("over")) break; String[] studentInfo = len.split(","); Student s = new Student(studentInfo[0], new int[] { Integer.parseInt(studentInfo[1]), Integer.parseInt(studentInfo[2]), Integer.parseInt(studentInfo[3]) }); // 當往HashSet中添加數據時,他會去找被添加對象的中實現了Comparable接口, studentSet.add(s); } return studentSet; } }
package xyxysjxy.io; import java.io.BufferedReader; import java.io.BufferedWriter; import java.io.FileWriter; import java.io.IOException; import java.io.InputStreamReader; import java.util.Comparator; import java.util.Iterator; import java.util.Set; import java.util.TreeSet; public class StudentInfoImport { public static void main(String[] args) throws IOException { BufferedWriter bw = new BufferedWriter( new FileWriter("f:\\student.txt")); Setss = StudentTools.getStudent(); Iterator is = ss.iterator(); while (is.hasNext()) { Student student = (Student) is.next(); bw.write(student.toString()); bw.newLine(); bw.flush(); } bw.close(); } } class Student implements Comparable { private String name; private int cn; private int math; private int en; private int sum; public Student(String name, int... is) { this.name = name; this.cn = is[0]; this.math = is[1]; this.en = is[2]; this.sum = cn + math + en; } @Override public String toString() { return "【name=" + name + "\tcn=" + cn + "\tmath=" + math + "\ten=" + en + "\tsum=" + sum + "】"; } @Override public boolean equals(Object obj) { if (!(obj instanceof Student)) throw new ClassCastException("不能強制的轉換"); Student s = (Student) obj; return s.name.equals(this.name) && s.sum == s.sum; } public int compareTo(Student o) { int sum = new Integer(this.sum).compareTo(new Integer(o.sum)); if (sum == 0) return this.name.compareTo(o.name); return sum; } @Override public int hashCode() { return sum * 78 + name.hashCode(); } } class StudentTools { public static Set getStudent() throws IOException { return getStudent(null); } public static Set getStudent(Comparator com) throws IOException { Set studentSet = null; if (com == null) studentSet = new TreeSet (); else studentSet = new TreeSet (com); BufferedReader br = new BufferedReader(new InputStreamReader(System.in)); String len = ""; while ((len = br.readLine()) != null) { if (len.equals("over")) break; String[] studentInfo = len.split(","); Student s = new Student(studentInfo[0], new int[] { Integer.parseInt(studentInfo[1]), Integer.parseInt(studentInfo[2]), Integer.parseInt(studentInfo[3]) }); // 當往HashSet中添加數據時,他會去找被添加對象的中實現了Comparable接口, studentSet.add(s); } return studentSet; } }通過上面的兩段代碼把這個執行的流程給大家講解一下:第一步:從控制台接收數值後封裝到了一個student對象當中去。
其實在treeSet內部其實封裝了一個TreeMap對象
當你調用了ADD方法時其實是調用了put方法。
while ((len = br.readLine()) != null) { if (len.equals("over")) break; String[] studentInfo = len.split(","); Student s = new Student(studentInfo[0], new int[] { Integer.parseInt(studentInfo[1]), Integer.parseInt(studentInfo[2]), Integer.parseInt(studentInfo[3]) });// 當往HashSet中添加數據時,他會去找被添加對象的中實現了Comparable接口, studentSet.add(s); } return studentSet; public TreeSet(Comparator super E> comparator) { this(new TreeMap<>(comparator)); }
第二步:首先他要進行檢查。這個三目運算符是這個意思:
首先他是判斷你在new treeset時候是否向其中傳遞了一個 comparator
對象,假如傳遞了那麼直接調用你傳進來的那個對象
但是你沒有傳遞進來那麼他就要做類型檢查了,
檢查的目的在與看你是否實現了Comparable假如實現了那麼就調用你自身的實現接口的方法
public V put(K key, V value) { Entryt = root; if (t == null) { compare(key, key); // type (and possibly null) check(L類型檢查) root = new Entry<>(key, value, null); size = 1; modCount++; return null; } //其實在第一次存儲對象時,所進行的比較是和自身比較 compare(key, key) final int compare(Object k1, Object k2) { return comparator==null ? ((Comparable super K>)k1).compareTo((K)k2) : comparator.compare((K)k1, (K)k2); }
第三步: 當檢查到你是實現了compare接口或是傳遞了一個compator對象時,他會調用你自身的實現方法進行比較。
通過返回值:-1,0,1來判斷你正要假如的值和treeset中的大小進行自動的排序的效果。