一、List接口
ArrayList,对象加入之后大都是为了取出,而不会长做删除或插入的动作,则使用ArrayList效率会更加好,但是经常在容器里面做删除添加动作,则使用LinkList会更加好(该类是利用链表实现的),故增加了象addFirst()、addLast()、getFirst()、getLast()、removeFirst()、removeFast()等,这样适合实现堆栈和队列。
二、Set接口
List容器中允许重复的对象,但是Set容器中的对象都是唯一的,介入Set 容器必须重新定义equals(),hasCode()方法,Set容器有自己一套排序规则,其规则是根据哈希法,所以加入HashSet容器的对象还必须重新定义hasCode()方法.
Set<String> set=new HashSet<String>();
Iterator iterator=set.iterator();
while(iterator.hasNext()){ iterator.next() };
也可以利用加强型进行访问元素:for(String name : set){ System.out.println(name); }
如果想要以加入的顺序显示,则可以用LinkedHashSet,此类是HashSet的子类,它在内部类实现时使用哈希玛进行排序但是在迭代的行为上像LinkList那样.
TreeSet实现了Set接口和SortSet接口,SortSet提供的相关方法让您有序的去处对应位置的对象,像first()、last()等方法,TreeSet是J2SE中唯一实现了SortSet接口的类,它使用了红黑树结构来加入对象将进行排序。如果对对象有自己的一套排序,要定义一个实现java.util,Comparator接口的对象,要实现compare()方法.
三、Map接口
Map接口的对象会将键(Key)映射至值(Value),值指的是要存入Map容器的对象,其对象不能有重复的键,Map拥有
自己的排序机制。
HashMap实现Map接口,在内部实现使用了哈希法,如果在迭代的时候想要以添加的顺序
来排序,则可以用HashMap子类LinkedHashMap。
其访问对象的代码:
Map<String,String> map=new HashMap<String,String>();
for(String value :map.values){
System.out.println(value);
}
TreeMap实现Map接口和SortMap接口,SortMap提供相关的方法让你有序地取出对应位置的对象,像firstKey(),lastKey()等方法,TreeMap是唯一实现SortedMap接口的类,它使用了红黑树结构来对加入的对象进行排序。
四、hashCode的作用
非常重要
小心内存泄露问题
用容器的时候为什么要覆盖equals()和hasCode()方法?上面是解释的原因
什么时候需要覆盖hashCode方法?
下面用例子进行证明:
package cn.itcast.day1; import java.util.Date; public class ReflectPoint { private Date birthday = new Date(); private int x; public int y; public String str1 = "ball"; public String str2 = "basketball"; public String str3 = "itcast"; public ReflectPoint(int x, int y) { super(); this.x = x; this.y = y; } @Override public int hashCode() { final int prime = 31; int result = 1; result = prime * result + x; result = prime * result + y; return result; } @Override public boolean equals(Object obj) { if (this == obj) return true; if (obj == null) return false; if (getClass() != obj.getClass()) return false; final ReflectPoint other = (ReflectPoint) obj; if (x != other.x) return false; if (y != other.y) return false; return true; } @Override public String toString(){ return str1 + ":" + str2 + ":" + str3; } public int getX() { return x; } public void setX(int x) { this.x = x; } public int getY() { return y; } public void setY(int y) { this.y = y; } public Date getBirthday() { return birthday; } public void setBirthday(Date birthday) { this.birthday = birthday; } }
package cn.itcast.day1; import java.io.FileInputStream; import java.io.InputStream; import java.util.ArrayList; import java.util.Collection; import java.util.HashMap; import java.util.HashSet; import java.util.Map; import java.util.Properties; public class ReflectTest2 { /** * @param args */ public static void main(String[] args) throws Exception{ // TODO Auto-generated method stub /*getRealPath();//金山词霸/内部 一定要记住用完整的路径,但完整的路径不是硬编码,而是运算出来的。*/ //InputStream ips = new FileInputStream("config.properties"); //InputStream ips = ReflectTest2.class.getClassLoader().getResourceAsStream("cn/itcast/day1/config.properties"); //InputStream ips = ReflectTest2.class.getResourceAsStream("resources/config.properties"); /* InputStream ips = ReflectTest2.class.getResourceAsStream("/cn/itcast/day1/resources/config.properties"); Properties props = new Properties(); props.load(ips); ips.close(); String className = props.getProperty("className"); Collection collections = (Collection)Class.forName(className).newInstance(); */ Collection collections = new HashSet(); ReflectPoint pt1 = new ReflectPoint(3,3); ReflectPoint pt2 = new ReflectPoint(5,5); ReflectPoint pt3 = new ReflectPoint(3,3); collections.add(pt1); collections.add(pt2); collections.add(pt3); collections.add(pt1); //pt1.y = 7; //collections.remove(pt1); System.out.println(collections.size()); } }
也就是说如果突然修改对象hashCode的值pt1.y=7,此容器想要移出这个对象,这个是办不到的,因此导致了内存的泄露
六、如何利用反射读取配置文件?用类加载器的方式管理资源和配置文件
InputStream ips = ReflectTest2.class.getClassLoader().getResourceAsStream("cn/itcast/day1/config.properties");
InputStream ips = ReflectTest2.class.getResourceAsStream("resources/config.properties")这个是第二种方式寻找配置文件.此文件假设存放在cn/itcast/day1/resources/config.properties
cn/itcast/day1/config.properties这个是所在的包中的文件路径,ReflectTest2类是在本类中找到装载器并加载所在的文件,这里注意类加载器再在class文件是从自己建的项目的路径开始加载,所以在寻找配置文件的时候一定要注意要加上所放配置文件的相对路径。所以在找文件的时候是在calsspath路径下找此文件。
Properties props = new Properties();
props.load(ips);
ips.close();
String className = props.getProperty("className");
Collection collections = (Collection)Class.forName(className).newInstance();
这样就能够根据className字符串动态的构建对象.
读取的文件格式为:className=java.util.ArrayList
具体源码请您参见张孝祥的源代码高级编程
还有疑问就是配置文件放在哪个路径下?