Java的各个容器List、Set、Map的创建使用和遍历以及Arrays类和Collections类的排序,查找,拷贝,填充等方法

JCF

-容器框架:为表示和操作容器而规定的一种标准体系结构
-对外的接口:容器中所能存放的抽象数据类型
-接口的实现:可复用的数据结构
-算法:对数据的查找和排序容器框架优点:提高数据存取效率,避免程序员重复劳动

JCF的集合接口是Collection(List,Set,Map)

-add,contains,remove,size
-iterator

JCF的迭代器接口Iterator

-hasNext判断是否有下一个元素
-next获取下一个元素
-remove删除某一个元素

JCF主要的数据结构实现类

-列表(List, ArrayLis, LinkedList)
-集合(Set, HashSet, TreeSet, LinkedHashSet)
-映射(Map, HashMap, TreeMap, LinkedHashMap)

JCF主要的算法类

-Arrays:对数组进行查找和排序等操作
-Collections: 对Collection及其子类进行排序和查找操作


列表List

-有序的Collection
-允许重复元素
-{1, 2, 4, {5, 2}, 1, 3}

List主要实现

-ArrayList(非同步的)
-LinkedList(非同步)
-Vector(同步)

ArrayList

-以数组实现的列表,不支持同步
-利用索引位置可以快速定位访问
-不适合指定位置的插入、删除操作
-适合变动不大,主要用于查询的数据
-和Java数组相比,其容量是可动态调整的
-ArrayList在元素填满容器时会自动扩充容器大小的50%
ArrayList只能装对象

创建
import java.util.ArrayList;
import java.util.Iterator;

public class ArrayListTest {
	public static void main(String[] a) {  
	    ArrayList<Integer> al = new ArrayList<Integer>();  //<Integer>表示泛型,说明al这个ArrayList里只能存放Integer这个类型的数据
	    al.add(3);  
	    //自动将普通的int变量3自动装箱为Integer(3)的对象,然后放入al里
	    al.add(2);          
	    al.add(1);  
	    al.add(4);  
	    al.add(5);  
	    al.add(6);  
	    al.add(new Integer(6));  
	  
	    System.out.print("The third element is  ");
	    System.out.println(al.get(3));//获得第四个元素
	    al.remove(3);  //删除第四个元素,后面元素往前挪动
	    al.add(3, 9);  //将9插入到第4个元素,后面元素往后挪动

输出

The third element is  4
遍历方法

创建ArrayList

		ArrayList<Integer> as = new ArrayList<Integer>(100000);//创建了包含100000个数据的ArrayList
		for (int i=0; i<100000; i++)
		{
			as.add(i);
		}
		traverseByIterator(as);  //iteration遍历,如下
		traverseByIndex(as);  //索引位置遍历,如下
		traverseByFor(as);    //for-each遍历,如下 
	}

iteration遍历

	public static void traverseByIterator(ArrayList<Integer> al)
	{
	 	Iterator<Integer> iter1 = al.iterator();  
	 	while(iter1.hasNext())
	 	{  
	     	iter1.next();  
	 	}
	}

索引位置遍历

	public static void traverseByIndex(ArrayList<Integer> al)
	{
	 	for(int i=0;i<al.size();i++)
	 	{
	    	al.get(i);
	 	}
	}

for循环遍历

	public static void traverseByFor(ArrayList<Integer> al)
	{
	    for(Integer item : al)
	    {
	    	;  //任意语句
	    }
	}

迭代器的速度最慢,索引方法和for方法速度接近


LinkedList

-以双向链表实现的列表,不支持同步
-可被当作堆栈、队列和双端队列进行操作
-顺序访问高效,随机访问较差,中间插入和删除高效
-适用于经常变化的数据

创建
import java.util.Iterator;
import java.util.LinkedList;

public class LinkedListTest {
	public static void main(String[] args) {
		LinkedList<Integer> ll = new LinkedList<Integer>();  
	    ll.add(3);  
	    ll.add(2);  
	    ll.add(5);  
	    ll.add(6);  
	    ll.add(6);  
	    System.out.println(ll.size()); //输出5
	    ll.addFirst(9);  //在头部增加9
	    ll.add(3, 10);   //将10插入到第四个元素,四以及后续的元素往后挪动
	    ll.remove(3);    //将第四个元素删除
遍历方法

创建LinkedList

		LinkedList<Integer> list = new LinkedList<Integer>();
		for (int i=0; i<100000; i++)
		{
	    	list.add(i);
		}
		traverseByIterator(list);   //iteration遍历,如下
		traverseByIndex(list);   //索引位置遍历,如下
		traverseByFor(list);     //for-each遍历,如下
	}

iteration遍历

	public static void traverseByIterator(LinkedList<Integer> list)
	{
		Iterator<Integer> iter1 = list.iterator();  
		while(iter1.hasNext())
		{  
	    	iter1.next();  
		}
	}

索引位置遍历

	public static void traverseByIndex(LinkedList<Integer> list)
	{
		for(int i=0;i<list.size();i++)
		{
	   		list.get(i);
		}
	}

for循环遍历

	public static void traverseByFor(LinkedList<Integer> list)
	{
		for(Integer item : list)
		{
	    	;  //任何语句
	 	}
	}

for循环遍历比迭代器快一点点,索引遍历最慢
ArrayList适用于较多查询的静态数据,而LinkedList适用于频繁增删的数据


Vector

-和ArrayList类似,可变数组实现的列表
-Vectora,适合在多线程下使用
-官方文档建议在非同步情况下,优先采用ArrayList

创建
import java.util.Enumeration;
import java.util.Iterator;
import java.util.Vector;

public class VectorTest {
	public static void main(String[] args) {
		Vector<Integer> v = new Vector<Integer>();
		v.add(1);
		v.add(2);
		v.add(3);
		v.remove(2);
		v.add(1, 5);
		System.out.println(v.size());
遍历方法

创建一个Vector

		Vector<Integer> v2 = new Vector<Integer>(100000);
		for (int i = 0; i < 100000; i++) {
			v2.add(i);
		}
		traverseByIterator(v2);//itertor遍历
		traverseByIndex(v2);//索引位置遍历
		traverseByFor(v2);//for-each遍历
		traverseByEnumeration(v2);//Enumeration遍历
	}

iterator遍历

	public static void traverseByIterator(Vector<Integer> v) {
		Iterator<Integer> iter1 = v.iterator();
		while (iter1.hasNext()) 
		{
			iter1.next();
		}
	}

索引位置遍历

	public static void traverseByIndex(Vector<Integer> v) {
		for (int i = 0; i < v.size(); i++) 
		{
			v.get(i);
		}
	}

for循环遍历

	public static void traverseByFor(Vector<Integer> v) {
		for (Integer item : v) 
		{
			;  //任意语句
		}
	}

Enumeration遍历(老方法)

public static void traverseByEnumeration(Vector<Integer> v) {
	for (Enumeration<Integer> enu = v.elements();enu.hasMoreElements();){  
			enu.nextElement();
		}
	}

for循环最快,其次是位置索引


Set集合

-确定性:对任意对象都能判定其是否属于某一个集合
-互异性:集合内每个元素都是无差异的,注意是内容差异
-无序性:集合内的顺序无关

Java中的集合接口Set

-HashSet (基于散列函数的集合,无序,不支持同步)
-TreeSet (基于树结构的集合,可排序的,不支持同步)
-LinkedHashSet(基于散列函数和双向链表的集合,可排序的,不支持同步)

HashSet

-基于HashMap实现的,可以容纳null元素,不支持同步
-add添加一个元素
-clear清除整个HashSet
-contains判定是否包含一个元素
-remove删除一个元素
-size大小
-retainAll计算两个集合交集

创建
import java.util.HashSet;
import java.util.Iterator;

public class HashSetTest {
	public static void main(String[] args) {
		HashSet<Integer> hs = new HashSet<Integer>();
		hs.add(null);
		hs.add(1000);
		hs.add(20);
		hs.add(3);
		hs.add(40000);
		hs.add(5000000);
		hs.add(3);                      //3 重复
		hs.add(null);                   //null重复
		System.out.println(hs.size());  //6
		if(!hs.contains(6))
		{
			hs.add(6);
		}
		System.out.println(hs.size());  //7
		hs.remove(4);
		System.out.println(hs.size());  //6
		hs.clear();
		System.out.println(hs.size());  //0
集合交集
	    HashSet<String> set1 = new HashSet<String>();
	    HashSet<String> set2 = new HashSet<String>();
	    
        set1.add("a");
        set1.add("b");
        set1.add("c");

        set2.add("c");
        set2.add("d");
        set2.add("e");

        set1.retainAll(set2);   
//set1的元素不在set2里面的全部被删除,那么set1只剩一个元素c
        System.out.println("交集是 "+set1);   //输出c
遍历方法

创建Set

		HashSet<Integer> hs2 = new HashSet<Integer>();
		for(int i=0;i<100000;i++)	
		{
			hs2.add(i);
		}
		traverseByIterator(hs2);   //迭代器遍历,如下
		traverseByFor(hs2);		   //for循环遍历,如下
	}

迭代器遍历

	public static void traverseByIterator(HashSet<Integer> hs)
	{
	    Iterator<Integer> iter1 = hs.iterator();  
	    while(iter1.hasNext())
	    {  
	        iter1.next();  
	    }
	}

for循环遍历

	public static void traverseByFor(HashSet<Integer> hs)
	{
	    for(Integer item : hs)
	    {
	    	;   //任意语句
	    }
	}
}

for循环速度比迭代器遍历快

LinkedHashSet

-继承HashSet,也是基于HashMap实现的,可以容纳null元素
-不支持同步
-方法和HashSet基本一致
add, clear, contains, remove, size
-通过一个双向链表维护插入顺序

创建
import java.util.Iterator;
import java.util.LinkedHashSet;

public class LinkedHashSetTest {
	public static void main(String[] args) {
		LinkedHashSet<Integer> lhs = new LinkedHashSet<Integer>();
		lhs.add(null);
		lhs.add(1000);
		lhs.add(20);
		lhs.add(3);
		lhs.add(40000);
		lhs.add(5000000);
		lhs.add(3);                      //3 重复
		lhs.add(null);                   //null 重复
		System.out.println(lhs.size());  //6
		if(!lhs.contains(6))
		{
			lhs.add(6);
		}
		System.out.println(lhs.size());  //7
		lhs.remove(4);
		System.out.println(lhs.size());  //6
		lhs.clear();
		System.out.println(lhs.size());  //0
遍历方法

创建LinkedHashSet

		LinkedHashSet<Integer> lhs2 = new LinkedHashSet<Integer>();
		for(int i=0;i<100000;i++)
		{
			lhs2.add(i);
		}
		traverseByIterator(lhs2);
		traverseByFor(lhs2);
	}	

迭代器遍历

	public static void traverseByIterator(LinkedHashSet<Integer> hs)
	{
	    Iterator<Integer> iter1 = hs.iterator();  
	    while(iter1.hasNext())
	    {  
	        iter1.next();  
	    }
	}

for循环遍历

	public static void traverseByFor(LinkedHashSet<Integer> hs)
	{
	    for(Integer item : hs)
	    {
	    	;  //任意语句
	    }
	}

LinkedHashSet是保留顺序的,其遍历顺序额插入顺序一致,而HashSet没有保留顺序,其遍历顺序无序

TreeSet

-基于TreeMap实现的,不可以容纳null元素,不支持同步
-add添加一个元素
-clear清除整个TreeSet
-contains判定是否包含一个元素
-remove删除一个元素
-size大小
-根据compareTo方法或指定Comparator排序

创建
import java.util.Iterator;
import java.util.TreeSet;

public class TreeSetTest {
	public static void main(String[] args) {
		TreeSet<Integer> ts = new TreeSet<Integer>();
		// ts.add(null);  错误,不支持null
		ts.add(1000);
		ts.add(20);
		ts.add(3);
		ts.add(40000);
		ts.add(5000000);
		ts.add(3);                      //3 重复
		System.out.println(ts.size());  //5
		if(!ts.contains(6))
		{
			ts.add(6);
		}
		System.out.println(ts.size());  //6
		ts.remove(4);
		System.out.println(ts.size());  //5
		lhs.clear();
		System.out.println(lhs.size());  //0
遍历方法

==TreeSet是按照所存储对象大小升序输出的 ==

创建TreeSet

		TreeSet<Integer> ts2 = new TreeSet<Integer>();
		for(int i=0;i<100000;i++)
		{
			ts2.add(i);
		}
		traverseByIterator(ts2);   //迭代器遍历
		traverseByFor(ts2);   //for循环遍历		
	}

迭代器遍历

	public static void traverseByIterator(TreeSet<Integer> hs)
	{
	    Iterator<Integer> iter1 = hs.iterator();  
	    while(iter1.hasNext())
	    {  
	        iter1.next();  
	    }

for循环遍历

	public static void traverseByFor(TreeSet<Integer> hs)
	{
	    for(Integer item : hs)
	    {
	    	;    //任意语句
	    }
	}
}

判定等价

-HashSet, LinkedHashSet, TreeSet的元素都只能是对象

-HashSet和LinkedHashSet判定元素重复的原则
-判定两个元素的hashCode返回值是否相同,若不同,返回false
-若两者hashCode相同,判定equals方法,若不同,返回false;否则返回true
- hashCode和equals方法是所有类都有的,因为Object类有 
-TreeSet判定元素重复的原则
-需要元素继承自Comparable接口
-比较两个元素的compareTo方法

HashSet, LinkedHashSet的例子

创建一个猫的类,只有一个成员变量size
class Cat
{
	private int size;
	public Cat(int size)
	{
		this.size = size;
	}
}

创建一个HashSet和LinkedHashSet,里面的成员是Cat

import java.util.HashSet;
public class JudgeRuleTest {
	public static void main(String[] args) {
		HashSet<Cat> hs = new HashSet<Cat>();
		hs.add(new Cat(1));
		hs.add(new Cat(2));
		hs.add(new Cat(3));
		hs.add(new Cat(3));
		System.out.println(hs.size()); //4
//最后的两只Cat(3),被判定不是相同的变量

		LinkedHashSet<Cat> lhs= new LinkedHashSet<Cat>();  
		lhs.add(new Cat(2));  
		lhs.add(new Cat(1));  
		lhs.add(new Cat(3));  
		lhs.add(new Cat(5));  
		lhs.add(new Cat(4));  
		lhs.add(new Cat(4));		
		System.out.println(lhs.size());  //6
//最后的两只Cat(4),被判定不是相同的变量
	}
}

Cat类本身没有hashCode(),而是继承Object类的,而Object的hashCode()会返回对象信息和内存地址经过运算后的一个int值。两个不同的Cat(4)对象,他们的hashCode()返回值是不同的

创建狗的类,成员属性size,重写了hashCode(),equals(),toString()函数
class Dog {
    private int size;
    public Dog(int s) {  ///构造函数
        size = s;
    }      
    public int getSize() {
		return size;
	}
	public boolean equals(Object obj2)   {    //重写Dog自己的equals()函数
    	if(0==size - ((Dog) obj2).getSize()) {
    		return true;
    	} else {
    		return false;
    	}
    }
    public int hashCode() {   //重写Dog自己的hashCode()函数
    	return size;
    }    
    public String toString() {
        return size + "";
    }
}

创建一个HashSet和LinkedHashSet,里面的成员是Dog

		HashSet<Dog> hs2 = new HashSet<Dog>();  
		hs2.add(new Dog(2));  
		hs2.add(new Dog(1));  
		hs2.add(new Dog(3));  
		hs2.add(new Dog(5));  
		hs2.add(new Dog(4)); 
		hs2.add(new Dog(4)); 
		System.out.println(hs2.size());  //5
//最后的两只Dog(4),被判定是相同的变量	
	
		LinkedHashSet<Dog> lhs2= new LinkedHashSet<Dog>();  
		lhs2.add(new Dog(2));  
		lhs2.add(new Dog(1));  
		lhs2.add(new Dog(3));  
		lhs2.add(new Dog(5));  
		lhs2.add(new Dog(4));  
		lhs2.add(new Dog(4)); 		
		System.out.println(lhs2.size());  //5
//最后的两只Dog(4),被判定是相同的变量	

Dog类本身改写了hashCode()方法,其返回值是具体的size,所以两个不同Dog(4),他们的hashCode()返回值是相同的
若两者hashCode相同,判定equals方法,若不同,返回false;否则返回true
重写时hashCode,equals,toString最好同时修改

创建Tiger类,包含成员变量size,实现Comparable接口
public class Tiger implements Comparable{
	private int size;
    public Tiger(int s) {
        size = s;    
    }        
    public int getSize() {
		return size;
	}    
	public int compareTo(Object o) {
        return size - ((Tiger) o).getSize();
    }
}

Tiger实现Comparable接口,所以必须实现compareTo方法来比较大小。compareTo方法具体规则如下:
int a =obj1. compareTo (obj2);
如果a>0,则obj1>obj2;
如果a= =0;则obj1=obj2;
如果a<0,则obj1<obj2

		HashSet<Tiger> hs3 = new HashSet<Tiger>();  
		hs3.add(new Tiger(2));  
		hs3.add(new Tiger(1));  
		hs3.add(new Tiger(3));  
		hs3.add(new Tiger(5));  
		hs3.add(new Tiger(4)); 
		hs3.add(new Tiger(4)); 
		System.out.println(hs3.size());  //6
		
		LinkedHashSet<Tiger> lhs3= new LinkedHashSet<Tiger>();  
		lhs3.add(new Tiger(2));  
		lhs3.add(new Tiger(1));  
		lhs3.add(new Tiger(3));  
		lhs3.add(new Tiger(5));  
		lhs3.add(new Tiger(4));  
		lhs3.add(new Tiger(4)); 		
		System.out.println(lhs3.size());  //6
	}

因为HashSet, LinkedHashSet判断对象是否相同,不根据compareTo

TreeSet的例子

添加到TreeSet的,需要实现Comparable接口,即实现compareTo方法

		TreeSet<Tiger> ts3 = new TreeSet<Tiger>();  
		ts3.add(new Tiger(2));  
		ts3.add(new Tiger(1));  
		ts3.add(new Tiger(3));  
		ts3.add(new Tiger(5));  
		ts3.add(new Tiger(4)); 
		ts3.add(new Tiger(4)); 
		System.out.println(ts3.size());  //5
	}

判断两个Tiger(4)是否相同,会调用compareTo方法,return size - ((Tiger) o).getSize();表明两个size一样返回0,说明他们是相同的


Map映射

-两个集合之间的元素对应关系
-一个输入对应到一个输出
-{1,张三}, {2,李四}, {Key, Value},键值对, K-V对

Java中Map

-Hashtable (同步,慢, 数据量小)
-HashMap (不支持同步,快,数据量大)
-Properties (同步,文件形式,数据量小)

Hashtable

-K-V对,K和V都不允许为null
-同步,多线程安全
-无序的
-适合小数据量
-主要方法: clear清空数据,contains等同containsValue是否包含某一个值,containsKey是否包含某一个Key,get根据Key获取相应的值,put增加新的K-V对,remove删除某一个K-V对,size返回数据大小

创建
import java.util.Enumeration;
import java.util.Hashtable;
import java.util.Iterator;
import java.util.Map;
import java.util.Map.Entry;

public class HashtableTest {
	public static void main(String[] args) {
		Hashtable<Integer,String> ht =new  Hashtable<Integer,String>();
		//ht.put(1, null); 编译不报错  运行报错
		//ht.put(null,1);  编译报错
		ht.put(1000, "aaa");
		ht.put(2, "bbb");
		ht.put(30000, "ccc");
		System.out.println(ht.contains("aaa"));
		System.out.println(ht.containsValue("aaa"));
		System.out.println(ht.containsKey(30000));
		System.out.println(ht.get(30000));
		
		ht.put(30000, "ddd");  //更新覆盖ccc
		ht.remove(2);	
		ht.clear();
遍历方法

创建Hashtable

		Hashtable<Integer,String> ht2 =new  Hashtable<Integer,String>();
		for(int i=0;i<100000;i++)
		{
			ht2.put(i, "aaa");
		}
		traverseByEntry(ht2);    //Entry迭代器遍历
		traverseByKeySet(ht2);   //KeySet迭代器遍历
		traverseByKeyEnumeration(ht2);		//KeyEnumeration迭代器遍历
	}

Entry迭代器遍历,Entry是指整个K-V对

	public static void traverseByEntry(Hashtable<Integer,String> ht)
	{
		Integer key;
		String value;
		Iterator<Entry<Integer, String>> iter = ht.entrySet().iterator();
		while(iter.hasNext()) 
		{
		    Map.Entry<Integer, String> entry = iter.next();
		    // 获取key
		    key = entry.getKey();
		    // 获取value
		    value = entry.getValue();
		}
	}
	

Key的iterator迭代器遍历,可以删除元素

	public static void traverseByKeySet(Hashtable<Integer,String> ht)
	{
		Integer key;
		String value;
		Iterator<Integer> iter = ht.keySet().iterator();
		while(iter.hasNext()) 
		{
		    key = iter.next();		    
		    // 获取value
		    value = ht.get(key);
		}
	}

Key的Enumeration迭代器遍历,只读

	public static void traverseByKeyEnumeration(Hashtable<Integer,String> ht)
	{
		Integer key;
		String value;
		Enumeration<Integer> keys = ht.keys();
		while(keys.hasMoreElements()) 
		{
		    key = keys.nextElement();   
		    // 获取value
		    value = ht.get(key);
		}
	}

Entry遍历最慢,Enumeration最快

HashMap

-K-V对, K和V都允许为null
-不同步,多线程不安全
-无序的
-主要方法: clear, containsValue, containsKey, get, put,remove, size

创建
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Map.Entry;

public class HashMapTest {
	public static void main(String[] args) {
		HashMap<Integer,String> hm =new  HashMap<Integer,String>();
		hm.put(1, null); 
		hm.put(null, "abc");  
		hm.put(1000, "aaa");
		hm.put(2, "bbb");
		hm.put(30000, "ccc");
		hm.containsValue("aaa");
		hm.containsKey(30000);
		hm.get(30000);
		hm.put(30000, "ddd");  //更新覆盖ccc
		hm.remove(2);
		hm.clear();
遍历方法

创建HashMap

		HashMap<Integer,String> hm2 =new  HashMap<Integer,String>();
		for(int i=0;i<100000;i++)
		{
			hm2.put(i, "aaa");
		}
		traverseByEntry(hm2);  //Entry迭代器遍历
		traverseByKeySet(hm2);		//KeySet迭代器遍历
	}

Entry迭代器遍历

	public static void traverseByEntry(HashMap<Integer,String> ht)
	{
		Integer key;
		String value;
		Iterator<Entry<Integer, String>> iter = ht.entrySet().iterator();
		while(iter.hasNext()) 
		{
		    Map.Entry<Integer, String> entry = iter.next();
		    // 获取key
		    key = entry.getKey();
		    // 获取value
		    value = entry.getValue();
		}
	}

KeySet迭代器遍历

	public static void traverseByKeySet(HashMap<Integer,String> ht)
	{
		Integer key;
		String value;
		Iterator<Integer> iter = ht.keySet().iterator();
		while(iter.hasNext()) 
		{
		    key = iter.next();		    
		    // 获取value
		    value = ht.get(key);
		}
	}

LinkedHashMap

-基于双向链表的维持插入顺序的HashMap TreeMap

创建
import java.util.LinkedHashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Map.Entry;

public class LinkedHashMapTest {
	public static void main(String[] args) {
		LinkedHashMap<Integer,String> hm=new LinkedHashMap<Integer,String>();
		hm.put(1, null); 
		hm.put(null, "abc");  
		hm.put(1000, "aaa");
		hm.put(2, "bbb");
		hm.put(30000, "ccc");
		hm.containsValue("aaa");
		hm.containsKey(30000);
		hm.get(30000);
		hm.put(30000, "ddd");  //更新覆盖ccc
		hm.remove(2);
		hm.clear();
遍历方法

创建LinkedHashMap

	LinkedHashMap<Integer,String> hm2=new LinkedHashMap<Integer,String>();
	for(int i=0;i<100000;i++)
	{
		hm2.put(i, "aaa");
	}
	traverseByEntry(hm2);   //Entry迭代器遍历
	traverseByKeySet(hm2);		//KeySet迭代器遍历
}

Entry迭代器遍历

	public static void traverseByEntry(LinkedHashMap<Integer,String> ht)
	{
		Integer key;
		String value;
		Iterator<Entry<Integer, String>> iter = ht.entrySet().iterator();
		while(iter.hasNext()) 
		{
		    Map.Entry<Integer, String> entry = iter.next();
		    // 获取key
		    key = entry.getKey();
		    // 获取value
		    value = entry.getValue();
		}
	 }

KeySet迭代器遍历

	
	public static void traverseByKeySet(LinkedHashMap<Integer,String> ht)
	{
		Integer key;
		String value;
		Iterator<Integer> iter = ht.keySet().iterator();
		while(iter.hasNext()) 
		{
		    key = iter.next();		    
		    // 获取value
		    value = ht.get(key);
		    //System.out.println("Key:" + key + ", Value:" + value);
		}
	}
}

TreeMap

-基于红黑树的Map,可以根据key的自然排序或者compareTo方法进行排序输出

创建
import java.util.TreeMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Map.Entry;

public class TreeMapTest {
	public static void main(String[] args) {
		TreeMap<Integer,String> hm =new  TreeMap<Integer,String>();
		hm.put(1, null); 
		//hm.put(null, "abc");  编译没错,运行报空指针异常  
		hm.put(1000, "aaa");
		hm.put(2, "bbb");
		hm.put(30000, "ccc");
		hm.containsValue("aaa");
		hm.containsKey(30000);
		hm.get(30000);
		hm.put(30000, "ddd");  //更新覆盖ccc
		hm.remove(2);
		hm.clear();
遍历方法

创建TreeMap

		TreeMap<Integer,String> hm2 =new  TreeMap<Integer,String>();
		for(int i=0;i<100000;i++)
		{
			hm2.put(i, "aaa");
		}
		traverseByEntry(hm2);    //Entry迭代器遍历
		traverseByKeySet(hm2);	//KeySet迭代器遍历
	}	

Entry迭代器遍历

	public static void traverseByEntry(TreeMap<Integer,String> ht)
	{
		Integer key;
		String value;
		Iterator<Entry<Integer, String>> iter = ht.entrySet().iterator();
		while(iter.hasNext()) 
		{
		    Map.Entry<Integer, String> entry = iter.next();
		    // 获取key
		    key = entry.getKey();
		    // 获取value
		    value = entry.getValue();
		}
	}

KeySet迭代器遍历

	public static void traverseByKeySet(TreeMap<Integer,String> ht)
	{
		Integer key;
		String value;
		Iterator<Integer> iter = ht.keySet().iterator();
		while(iter.hasNext()) 
		{
		    key = iter.next();		    
		    // 获取value
		    value = ht.get(key);
		    //System.out.println("Key:" + key + ", Value:" + value);
		}
	}
}

Properties

-继承于Hashtable
-可以将K-V对保存在文件中
-适用于数据量少的配置文件
-从文件加载的load方法, 写入到文件中的store方法
-获取某一个Key所对应的Value用getProperty,写入一个K-V对用setProperty
-如需要将 K-V 存储为文件,可采用 Properties 类

常规操作
import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.Enumeration;
import java.util.Properties;

//关于Properties类常用的操作
public class PropertiesTest {
    public static String GetValueByKey(String filePath, String key) {
        Properties pps = new Properties();
        try {
            InputStream in = new BufferedInputStream (new FileInputStream(filePath));  
            pps.load(in); //所有的K-V对都加载了
            String value = pps.getProperty(key);    //根据Key读取Value
            return value;     
        }catch (IOException e) {
            e.printStackTrace();
            return null;
        }
    }
写入
    //写入Properties信息
    public static void WriteProperties (String filePath, String pKey, String pValue) throws IOException {
        File file = new File(filePath);
    	if(!file.exists())
    	{
    		file.createNewFile();
    	}
    	Properties pps = new Properties();
        
        InputStream in = new FileInputStream(filePath);
        //从输入流中读取属性列表(键和元素对) 
        pps.load(in);
        //调用 Hashtable 的方法 put。使用 getProperty 方法提供并行性。  
        //强制要求为属性的键和值使用字符串。返回值是 Hashtable 调用 put 的结果。
        OutputStream out = new FileOutputStream(filePath);
        pps.setProperty(pKey, pValue);
        //以适合使用 load 方法加载到 Properties 表中的格式,  
        //将此 Properties 表中的属性列表(键和元素对)写入输出流  
        pps.store(out, "Update " + pKey + " name");
        out.close();
    }
读取
    //读取Properties的全部信息
    public static void GetAllProperties(String filePath) throws IOException {
        Properties pps = new Properties();
        InputStream in = new BufferedInputStream(new FileInputStream(filePath));
        pps.load(in); //所有的K-V对都加载了
        Enumeration en = pps.propertyNames(); //得到文件的名字
        
        while(en.hasMoreElements()) {
            String strKey = (String) en.nextElement();
            String strValue = pps.getProperty(strKey);
        }
    }

工具类

JCF中工具类

-不存储数据,而是在数据容器上,实现高效操作
-排序
-搜索
-Arrays 类
-Collections 类

Arrays:处理对象是数组

-排序:对数组排序, sort/parallelSort
-查找:从数组中查找一个元素, binarySearch
-批量拷贝:从源数组批量复制元素到目标数组, copyOf
-批量赋值:对数组进行批量赋值, fill
-等价性比较:判定两个数组内容是否相同, equals

import java.util.Arrays;
import java.util.Random;

public class ArraysTest { 
	public static void main(String[] args) {
		testSort();
		testSearch();
		testCopy();
		testFill();
		testEquality();
	}

sort()排序

	public static void testSort() {
		Random r = new Random();
		int[] a = new int[10];
		for(int i=0;i<a.length;i++)	{
			a[i] = r.nextInt();  //返回下一个int随机数
		}
		System.out.println("===============测试排序================");
		System.out.println("排序前");
		for(int i=0;i<a.length;i++)	{
			System.out.print(a[i] + ",");
		}
		System.out.println("排序后");
		Arrays.sort(a);         //用来排序的函数
		for(int i=0;i<a.length;i++)	{
			System.out.print(a[i] + ",");
		}		
	}

输出

===============排序================
排序前
-956351502,1319671543,514166787,2025415429,1194844482,50373231,591196643,-312467671,672486313,-1919848267,
排序后
-1919848267,-956351502,-312467671,50373231,514166787,591196643,672486313,1194844482,1319671543,2025415429,

binarySearch()查找

	public static void testSearch() {
		Random r = new Random();
		int[] a = new int[10];
		for(int i=0;i<a.length;i++)
		{
			a[i] = r.nextInt();
		}
		a[a.length-1] = 10000;
		System.out.println("===========测试查找============");
		System.out.println("10000 的位置是" + Arrays.binarySearch(a, 10000));
	}

输出

===========查找============
10000 的位置是-3

copyOf()拷贝

	public static void testCopy() {
		Random r = new Random();
		int[] a = new int[10];
		for(int i=0;i<a.length;i++)
		{
			a[i] = r.nextInt();
		}
		int[] b = Arrays.copyOf(a, 5);
		System.out.println("===========测试拷贝前五个元素============");
		System.out.print("源数组:");
		for(int i=0;i<a.length;i++)
		{
			System.out.print(a[i] + ",");
		}
		System.out.println();
		System.out.print("目标数组:");
		for(int i=0;i<b.length;i++)
		{
			System.out.print(b[i] + ",");
		}
		System.out.println();
	}

输出

===========拷贝前五个元素============
源数组:-1978377658,782629928,-1800820484,787311198,1385421194,1893651335,1067858632,1740898767,-1886555356,-884417663,
目标数组:-1978377658,782629928,-1800820484,787311198,1385421194,

fill()批量赋值

	public static void testFill() {
		int[] a = new int[10];
		Arrays.fill(a, 100);
		Arrays.fill(a, 2, 8, 200);
		System.out.println("===========测试批量赋值============");
		System.out.print("数组赋值后:");
		for(int i=0;i<a.length;i++)
		{
			System.out.print(a[i] + ",");
		}
		System.out.println();
	}

输出

===========批量赋值============
数组赋值后:100,100,200,200,200,200,200,200,100,100,

equals()测试

	public static void testEquality() {
		int[] a = new int[10];
		Arrays.fill(a, 100);
		int[] b = new int[10];
		Arrays.fill(b, 100);		
		System.out.println(Arrays.equals(a, b));
		b[9] = 200;
		System.out.println(Arrays.equals(a, b));
	}
}

输出

true
false

Collections:处理对象是Collection及其子类,例如Map,Set,List等

-排序:对List进行排序, sort
-搜索:从List中搜索元素, binarySearch
-批量赋值: 对List批量赋值, fill
-最大、最小:查找集合中最大/小值, max, min
-反序:将List反序排列, reverse

mport java.util.ArrayList;
import java.util.Collections;

public class CollectionsTest {
	public static void main(String[] args) {
		ArrayList<Integer> list = new ArrayList<Integer>();
        list.add(1);
        list.add(12);
        list.add(2);
        list.add(19);
         
        // 排序
        Collections.sort(list);
        // 检索
        System.out.println("元素所在的索引值是:" + Collections.binarySearch(list, 12));
        //最大最小
        System.out.println("最大值:" + Collections.max(list));
        System.out.println("最小值:" + Collections.min(list));
        Collections.reverse(list); //翻转不需要用到排序
        Collections.fill(list, 100); //全部赋值为100
	}
}

输出

元素所在的索引值是:2
最大值:19
最小值:1

对象比较

-对象实现Comparable接口(需要修改对象类)
-compareTo方法
	>返回1,
	= =返回0,
	<返回-1
-Arrays和Collections在进行对象sort时, 自动调用该方法
-新建Comparator (适用于对象类不可更改的情况)
-compare方法
	>返回1,
	= =返回0,
	<返回-1
-Comparator比较器将作为参数提交给工具类的sort方法

对象排序需要遵循一定的规则。
Integor对象可以自然按照数值大小进行排序
而普通的自定义对象无法排序。因此,普通的自定义对象需要实现Comparabl换口,按照 compareTo方法所规定的原则进行排序

例子

普通的自定义对象
import java.util.Arrays;
//person实现接口Comparable,泛型Person
public class Person implements Comparable<Person> {
	String name;
	int age;

	public String getName() {
		return name;
	}

	public int getAge() {
		return age;
	}
//构造函数
	public Person(String name, int age) {
		this.name = name;
		this.age = age;
	}
//实现Comparable里的compareTo函数
	public int compareTo(Person another) {
		int i = 0;
		i = name.compareTo(another.name); // 使用字符串的比较,字符串可以直接使用compareTo
		if (i == 0) {
			// 如果名字一样,比较年龄, 返回比较年龄结果
			return age - another.age;
		} else {
			return i; // 名字不一样, 返回比较名字的结果.
		}
	}

	public static void main(String... a) {
		Person[] ps = new Person[3];
		ps[0] = new Person("Tom", 20);
		ps[1] = new Person("Mike", 18);
		ps[2] = new Person("Mike", 20);

		Arrays.sort(ps);
		for (Person p : ps) {
			System.out.println(p.getName() + "," + p.getAge());
		}
	}
}

输出

//先对名字排序,再对年纪排序
Mike,18
Mike,20
Tom,20
不可变的对象

假设Person2不可更改

public class Person2 {
	private String name;
    private int age;
    
	public String getName() {
		return name;
	}
	public int getAge() {
		return age;
	}

    public Person2(String name, int age)
    {
    	this.name = name;
    	this.age = age;
    }
}

创建Person2Comparator实现Comparator接口

import java.util.Arrays;
import java.util.Comparator;

public class Person2Comparator implements Comparator<Person2> {
//实现Comparator里的compare方法
	public int compare(Person2 one, Person2 another) {
		int i = 0;
		i = one.getName().compareTo(another.getName());// 使用字符串的比较,字符串可以直接使用compareTo
		if (i == 0) {
			// 如果名字一样,比较年龄,返回比较年龄结果
			return one.getAge() - another.getAge();
		} else {
			return i; // 名字不一样, 返回比较名字的结果.
		}
	}

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Person2[] ps = new Person2[3];
		ps[0] = new Person2("Tom", 20);
		ps[1] = new Person2("Mike", 18);
		ps[2] = new Person2("Mike", 20);

		Arrays.sort(ps, new Person2Comparator()); //不可变对象的sort参数多了一个创建的Person2Comparator类
		for (Person2 p : ps) {
			System.out.println(p.getName() + "," + p.getAge());
		}
	}
}

输出

Mike,18
Mike,20
Tom,20
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值