JAVA自学教程之(常用对象API)— Set集合:HashSet集合演示。
随着Java学习的深入,感觉大一时搞了一年的ACM,简直是明智之举,Java里很多数据结构、算法类的东西,理解起来就轻松多了
Set集合下有两大子类开发常用 HashSet集合 、TreeSet集合
Set集合的元素是不重复且无序
一、HashSet集合
API文档解释:此类实现 Set 接口,由哈希表(实际上是一个 HashMap 实例)支持。它不保证 set 的迭代顺序;特别是它不保证该顺序恒久不变。此类允许使用null 元素。
此类为基本操作提供了稳定性能,注意,此实现不是同步的。
由上可以总结出:HashSet集合的方法:内部数据结构是哈希表,且不同步,无论重复元素有多少,只存一个。
- import java.util.HashSet;
- import java.util.Iterator;
- public class Main
- {
- public static void main(String[] args)
- {
- HashSet hash = new HashSet();
- hash.add(“123″);
- hash.add(“456″);
- hash.add(“asd”);
- hash.add(“789″);
- Iterator it = hash.iterator();
- while(it.hasNext()){
- System.out.println(it.next());
- }
- }
- }
哈希表
数据经过哈希算法存储,会经过两次判断,第一此判断位置,第二次会判断内容,比如“ab”已经存储了,“ba”经过算法得到的位置是“ab”的位置,这时要经过第二次判断,确定内容是否相同,不相同会通过过算法得到新的位置,ACM里一般会经过线性探测再散列或者是链地址法
总结
哈希表判断元素是否相同:
1.判断的是两个元素的哈希值是否相同,如果相同,再判断两个对象的内容是否相同
2.判断哈希值相同,HashCode方法(返回此字符串的哈希码),判断内容相同,equals方法
注:哈希值不同,就不需要第二次判断内容是否相同
哈希表演示
- import java.util.HashSet;
- import java.util.Iterator;
- class Man extends Object//必须继承Object类才能复写HshCode,equals
- {
- private String name;
- private int age;
- public Man() {
- super();
- // TODO Auto-generated constructor stub
- }
- public Man(String name, int age) {
- super();
- this.name = name;
- //System.out.println(“1号”+this);
- this.age = age;
- }
- @Override
- public int hashCode() {
- final int prim = 31;
- //System.out.println(“namecode = ”+name.hashCode());
- return name.hashCode()+age*prim;
- }
- @Override
- public boolean equals(Object obj) {
- if(this == obj)
- return true;
- //System.out.println(“2号”+this);
- if(!(obj instanceof Man))
- throw new ClassCastException(“类型错误”);
- Man m = (Man)obj;
- return this.name.equals(m.name) && this.age == m.age;
- }
- public String getName() {
- return name;
- }
- public void setName(String name) {
- this.name = name;
- }
- public int getAge() {
- return age;
- }
- public void setAge(int age) {
- this.age = age;
- }
- }
- public class Main
- {
- public static void main(String[] args)
- {
- HashSet hash = new HashSet();
- hash.add(new Man(“a”,11));
- hash.add(new Man(“b”,12));
- hash.add(new Man(“c”,13));
- hash.add(new Man(“a”,11));
- Iterator it = hash.iterator();
- while(it.hasNext()){
- Man M = (Man)it.next();
- System.out.println(M.getName()+”…..”+M.getAge());
- }
- }
- }
特别注意:上述代码的1号和2号两个this,代表的对象不同,不能混淆
练习
关于ArrayList的演示
- import java.util.ArrayList;
- import java.util.HashSet;
- import java.util.Iterator;
- class Man extends Object
- {
- private String name;
- private int age;
- public Man() {
- super();
- // TODO Auto-generated constructor stub
- }
- public Man(String name, int age) {
- super();
- this.name = name;
- this.age = age;
- }
- @Override
- public boolean equals(Object obj) {
- if(this == obj)
- return true;
- if(!(obj instanceof Man))
- throw new ClassCastException(“类型错误”);
- Man m = (Man)obj;
- return this.name.equals(m.name) && this.age == m.age;
- }
- public String getName() {
- return name;
- }
- public void setName(String name) {
- this.name = name;
- }
- public int getAge() {
- return age;
- }
- public void setAge(int age) {
- this.age = age;
- }
- }
- public class Main
- {
- public static void main(String[] args)
- {
- ArrayList AL = new ArrayList();
- AL.add(new Man(“a”,11));
- AL.add(new Man(“b”,12));
- AL.add(new Man(“c”,13));
- AL.add(new Man(“a”,11));
- printf(AL);
- AL = ArrayListHashDemo(AL);
- printf(AL);
- System.out.println(AL.remove(new Man(“a”,11)));
- printf(AL);
- }
- public static ArrayList ArrayListHashDemo(ArrayList al) {
- ArrayList temp = new ArrayList();
- Iterator it = al.iterator();
- while(it.hasNext())
- {
- Object obj = it.next();
- if(!temp.contains(obj))
- temp.add(obj);
- }
- return temp;
- }
- public static void printf(ArrayList al)
- {
- Iterator it = al.iterator();
- while(it.hasNext())
- {
- Man man = (Man)it.next();
- System.out.print(man.getName()+”..”+man.getAge()+”,”);
- }
- System.out.printf(“\n”);
- }
- }
API文档关于contains的解释:如果列表包含指定的元素,则返回 true。更确切地讲,当且仅当列表包含满足(o==null ? e==null : o.equals(e)) 的元素e 时才返回true。
所以对于ArrayList集合,contains的判断与equals有关,而HashSet与HashCode和equals有关
- System.out.println(AL.remove(new Man(“a”,11)));//同理,remove也是有equals有关,只判断内容