黑马程序员———集合2以及部分1.5新特性

来源:互联网 发布:mac找不到启动磁盘 编辑:程序博客网 时间:2024/05/22 11:59

------Java培训、Android培训、iOS培训、.Net培训、期待与您交流! -------

Map

Map集合:该集合存储键值对,一对一对往里存,而且要保证键的唯一性;

HashTable:底层是哈希表数据结构,不可以存入null键null值。该集合时线程同步的。Jdk1.0 效率低

HashMap:底层是哈希表数据结构,允许使用null值和null键,该集合是不同步的。将HashTable替代,jdk1.2 效率高

TreeMap 底层是二叉树数据结构,线程不同步,可以用于给Map集合中的键进行排序

其实Set底层就是使用了Map集合

Map中常用方法:

1、添加

        V put(K key,V value);//添加元素,如果出现添加时,相同的键,那么后添加的值会覆盖原有键对应值,并put方法会返回被覆盖的值。

        void putAll(Map <? extends K,? extends V> m);//添加一个集合

2、删除

        clear();//清空

        V remove(Object key);//删除指定键值对

3、判断

        containsKey(Objectkey);//判断键是否存在

        containsValue(Objectvalue)//判断值是否存在

        isEmpty();//判断是否为空

4、获取

        V get(Object key);//通过键获取对应的值

        size();//获取集合的长度

        Collection<V>value();//获取Map集合中所以得值,返回一个Collection集合

还有两个取出方法,接下来会逐个讲解:

        Set<Map.Entry<K,V>>entrySet();

        Set<K>  keySet();

注:HashMap集合可以通过get()方法的返回值来判断一个键是否存在,通过返回null来判断。

Map取出元素的第一种方式:

import java.util.*;public class MapDemo {public static void main(String[] args) {//定义一个Map集合Map<Integer,String> map = new HashMap<Integer,String>();//添加元素map.put(1, "aaa");map.put(2, "bbb");map.put(3, "ccc");map.put(4, "ddd");//取出键值的Set视图Set<Integer> set = map.keySet();//迭代Iterator<Integer> it = set.iterator();while(it.hasNext()){Integer key = it.next();String value = map.get(key);System.out.println(key+"="+value);}}}

Map取出元素的第二种方式:

 

import java.util.HashMap;import java.util.Map;import java.util.*;public class MapDemo2 {public static void main(String[] args) {//定义一个Map集合Map<Integer,String> map = new HashMap<Integer,String>();//添加元素map.put(1, "aaa");map.put(2, "bbb");map.put(3, "ccc");map.put(4, "ddd");//得到存有Map中映射关系的Set视图Set<Map.Entry<Integer, String>> sme = map.entrySet();//迭代Iterator<Map.Entry<Integer, String>> it = sme.iterator();while(it.hasNext()){Map.Entry<Integer, String> me = it.next();Integer key = me.getKey();String value = me.getValue();System.out.println(key+"="+value);}}}

练习:统一每个字母在一串字符串中出现的次数

/*统计字符串中每个字母出现的次数 * 思路:1,将字符串转换成字符数组,因为要对每一个字母进行操作 * 2,定义一个Map集合,因为打印结果的字母有顺序,所以使用TreeMap集合 * 3,遍历字符数组 * 将每一个字母作为键去查Map集合 * 如果返回null ,将该字母和1存入到map集合中 * 如果返回不是null,说明该字母在map集合已经存在并有对应次数 * 那么就获取该次数并进行自增,然后将该字母和自增后的次数存入到map集合中,覆盖原有键所对应的次数 * 4,将map集合中数据变成指定的字符串形式返回 * */import java.util.*;public class MapDemo3 {public static void main(String[] args) {//测试String str = "jdsljfweonvlnlj";str = count(str);System.out.println(str);}public static String count(String str){//定义一个StringBuilderStringBuilder sb = new StringBuilder();//定义一个MapTreeMap<Character,Integer> tm = new TreeMap<Character,Integer>();//将传入的字符串转化为数组char[] ch = str.toCharArray();//查看数组中的每个元素是否是Map的键值,如果是将此键值的值加1然后讲这对键和键值继续存入Map 集合中//如果不是,将此元素当做键一当做值存入Map集合中for(int i = 0 ; i < ch.length; i++){if(tm.get(ch[i]) == null){tm.put(ch[i], 1);}else{int value = tm.get(ch[i]);value++;tm.put(ch[i],value);}}//迭代Map集合,并将其化为指定的字符串形式返回Set<Character> set = tm.keySet();Iterator<Character> it = set.iterator();while(it.hasNext()){Character key = it.next();Integer value = tm.get(key);sb.append(key+"("+value+")");}return sb.toString();}}

练习二:

/* * 有学校czbk  学校中包括两个班级jyb  和 yrb   每个班级包括学生,学号和姓名*/import java.util.*;public class MapDemo5 {public static void main(String[] args) {//学校集合czbkHashMap<String,HashMap<Integer,String>> czbk = new HashMap<String,HashMap<Integer,String>>();//班级yrb集合HashMap<Integer,String> yrb = new HashMap<Integer,String>();//班级jyb集合HashMap<Integer,String> jyb = new HashMap<Integer,String>();//添加元素yrb.put(111, "lis1");yrb.put(222, "lis2");yrb.put(333, "lis3");jyb.put(444, "wang4");jyb.put(555, "wang5");jyb.put(666, "wang6");czbk.put("yrb", yrb);czbk.put("jyb", jyb);print(czbk);   }//打印集合public static void print(HashMap<String,HashMap<Integer,String>> czbk){//获取学校的键值set视图Set<String> set = czbk.keySet();//迭代Iterator<String> it = set.iterator();while(it.hasNext()){String key = it.next();System.out.println(key);HashMap<Integer,String> value = czbk.get(key);//打印班级名称Set<Integer> set_2 = value.keySet();//迭代Iterator<Integer> it_2 = set_2.iterator();while(it_2.hasNext()){Integer key_2 = it_2.next();String value_2 = value.get(key_2);System.out.println("学号: "+key_2+"姓名:+ "+value_2);}}}}

Collection:一个集合接口。它提供了对集合对象进行基本操作的通用接口方法。Collection接口在Java类口中有很多

具体的实现。Collection接口的意义是为各种具体的集合提供了最大化的统一操作方式。

练习:Collections中的二分查找和sort方法:

代码:

import java.util.*;public class CollectionsDemo {    //测试类public static void main(String[] args) {ArrayList<String> alist = new ArrayList<String>();alist.add("aaaa");alist.add("bbb");alist.add("cc");alist.add("d");    Collections.sort(alist, new Cmp_1());int index = binarySearch(alist,"bbb",new Cmp_1());System.out.println(alist);System.out.println(index);}//Collections的二分查找的实现原理public static int binarySearch(ArrayList<String> alist,String key,Comparator<String> cmp){int max = alist.size()-1,min = 0,mid;while(min<= max){mid = (max + min)>>1;int num =cmp.compare(alist.get(mid), key);if(num > 0)max = mid -1;else if(num < 0)min = mid+1;else return mid;}return -min-1;}}//自定义的比较器class Cmp_1 implements Comparator<String>{@Overridepublic int compare(String arg0, String arg1) {int num = new Integer(arg0.length()).compareTo(new Integer(arg1.length()));if(num == 0)return arg0.compareTo(arg1);return num;}}


Arrays 数组工具类

此类包含用来操作数组(比如排序和搜索)的各种方法。此类还包含一个允许将数组作为列表来查看的静态工厂。

方法:将数组转换为集合

把数组转换为集合有什么好处?

可以使用集合的思想和方法来操作数组中的元素。

注意:将数组变成集合,不可以使用集合的增删方法。因为数组的长度是固定的。

如果增删,那么会抛出UnsupportOperationException

如果数组中的元素都是对象,那么变成集合时,数组汇总的元素就直接转成集合中的元素。如果数组中的元素都是基

本数据类型,那么会将该数组作为集合中的元素存在。

Arrays常用方法:

static <T> List<T> asList(T... a) //返回一个指定数组支持的固定大小的列表

示例代码:

Integer[] it  = {1,2,3,4,5,6};List<Integer> al = Arrays.asList(it);al.contains(2);//判断是否包含某个元素    al.get(2);//获取指定角标值al.indexOf(3);//获取某个元素第一次出现的al.isEmpty();//判断集合是否为空al.iterator();//返回集合的迭代器al.set(2, 2);//设置某个角标的值al.size();//返回集合的元素数al.subList(2, 4);//截取子集合


static int binarySerach(int[] a, int key) 使用二分查找法来搜索指定的int型数组,已获得指定的值

static int binarySearch(int[] a , int fromIndex,int toIndex,int key )使用二分搜索法来搜索指定的int型数组的范围,以获

取指定的值

static int[] copyOf(int [] original, int newLength)复制指定的数组,截取或用0填充(如有必要),以使副本具有指定的

长度

static int[] copyOfRange(int[] original, int form , int to )将指定数组的指定范围复制到一个新数组

static void fill(int[] a , int val )将指定的int值分配给指定int型数组的每个元素

static void fill(int[] a ,int fromIndex, int toIndex, int val)将指定的int值分配给指定int型数组指定范围中的每个元素

static void sort(int[] a )对指定int型数组按升序进行排序

static void sort(int[] a ,int formIndex,int toIndex)对指定int型数组的指定范围按数组升序进行排序

static String toString(int[] a )返回指定数组内容的字符串表现形式

将集合转换成数组:

为什么要将集合变为数组?

为了限定对元素的操作,不需要进行增删了。

在上述方法中,当指定类型的数组长度小于集合的size,那么该方法内会创建一个新的数组,长度为集合的size。当

指定类型的数组长度大于了集合的size,就不会创建新数组,而是使用传递进来的数组。

<T> T[] toArray(T[] a ) 返回包含此Collection中所有元素的数组。返回数组的运行时类型与指定数组的运行时类型相

同。

 

示例代码:

<span style="font-size:18px;"> ArrayList<Integer> al = new ArrayList<Integer>();al.add(1);al.add(2);al.add(3);al.add(4);al.add(5);al.add(6);al.add(7);Integer[] a =al.toArray(new Integer[0]);for(int i = 0; i < a.length; i++){System.out.print(a[i]+" ");}</span>

增强for循环

实现Iterable接口允许对象成为“foreach”语句的目标

格式:

for(数据类型 变量名: 被遍历的集合(Collection)或数组)

{

}

对集合进行遍历:只能获取集合元素,但是不能对集合进行操作。迭代器除了遍历,还可以进行remove集合中的元

素的动作。如果是用ListIterator,还可以在遍历过程中对集合进行增删改查的动作。

传统for和高级for有什么区别:

高级for 有一个局限性,必须由被遍历的目标,传统for 可以没有。

建议在遍历数组的时候,还是希望使用传统for,因为传统for可以定义脚标。

示例代码:

 ArrayList<Integer> al = new ArrayList<Integer>();al.add(1);al.add(2);al.add(3);al.add(4);al.add(5);al.add(6);al.add(7);    //增强for遍历集合for(Integer i : al){System.out.print(i+" ");}System.out.println();Integer[] a =al.toArray(new Integer[0]);//增强for遍历数组for(Integer i : a){System.out.print(i+" ");}System.out.println();//传统for遍历数组for(int i = 0; i < a.length; i++){System.out.print(a[i]+" ");}

Map使用增强for迭代:

 

 
                HashMap<Integer,String> hm = new HashMap<Integer,String>();hm.put(1, "java01");hm.put(2, "java02");hm.put(3, "java03");hm.put(4, "java04");Set<Integer> keySet = hm.keySet();for(Integer i : keySet){String value = hm.get(i);System.out.println(i+":::"+value);}

 

可变参数:

可变参数:Java1.5增加的新特性。可变参数适用于参数个数不确定,类型确定的情况,Java把可变参数当做数组处

理。注意:可变参数必须位于参数的最后一项。当可变参数

个数多于一个时,必须有一个不是最后一项,所以只支持一个可变参数。因为参数个数不定,所以当其后面还有相同

类型参数时,Java无法区分传入的参数属于前一个可变参数还是后边的参数,所以只能让可变参数位于最后一项。

其实可变参数就是数组参数的简写形式。不用每一次都手动的建立数组对象。只要将要操作的元素作为参数传递即

可。隐式将这些参数封装成了数组。

<span style="font-size:18px;">public class Demo3 {public static void main(String[] args) {//传入参数show(1,2,3,4,5,6,7);System.out.println();//传入数组int[] arr = {1,2,3,4,5,6,7,8};show(arr);}//可变参数public static void show(int... arr){for(int i = 0; i < arr.length; i++){System.out.print(arr[i]+" ");}}}</span>

态导入可以使被导入的静态变量和静态方法在当前类直接可见,使用这些静态成员无需再给出它们的类名

例如:import staticjava.util.Arrays.*;

注意:当类名重名时,需要指定具体的包名。

当方法重名时,指定具备所属的对象或者类。

 

 

 



 

 


 

 

 

 

 

 

 

 

 

 

 




 

 

 

 

0 0
原创粉丝点击