Day 9:双列集合Map及实现该接口的类的常用方法

为什么要学双列集合?

因为单列集合无法处理映射关系,会有成对出现的数据

Map接口  如果是实现了Map接口的集合类,具备的特点: 存储的数据都是以键值对的形式存在的,键不可重复,值可以重复

  Map接口的方法:
      添加:
         put(K key, V value)
         putAll(Map<? extends K,? extends V> m) 
      删除
         remove(Object key)
         clear()

      获取:
         get(Object key)
         size() 
      判断:
         containsKey(Object key)
         containsValue(Object value)
         isEmpty()

    迭代:
        keySet()
        values()
        entrySet()

import java.util.HashMap;
import java.util.Map;

public class Demo1 {
    public static void main(String[] args) {
        Map<String,String> map = new HashMap<String,String>();
        //添加
        map.put("李杰","李英");
        map.put("黎晨辉","王成娟");
        map.put("蛮王","艾希");
        map.put("zhangsan", "999999");
        System.out.println(map.put("蛮王", "寡妇"));//寡妇把艾希替换了返回艾希,被替换的
        System.out.println(map.put("zhangsan", "value"));//如果前面没有添加就返回null
        System.out.println(map);
        Map<String,String> map1 = new HashMap<String,String>();
        map1.put("文章", "马伊琍");
        map1.put("谢霆锋","张柏芝");
        map1.put("成龙", "林凤娇");
        map.putAll(map1);
        System.out.println(map);
        //删除
        //System.out.println("被删除的数据:  "+map.remove("蛮王"));//根据键值删除数据,返回的是删除的建对应的值
        //System.out.println(map);
        //map.clear();
        //System.out.println(map);
        
        //获取
        System.out.println(map.get("蛮王"));//根据指定的建获取值
        System.out.println(map.size());//键值对个数
        
        //判断
        System.out.println(map.containsKey("蛮王"));//判断集合是否包含指定的建
        System.out.println(map.containsValue("张柏芝"));//判断集合是否包含指定的值
        System.out.println(map.isEmpty());
    }
    
}
//双列集合没有迭代器,所以在遍历双列集合的时候要返回单列集合,然后借用单列集合的迭代器
import java.util.Collection;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;

public class Demo2 {
    public static void main(String[] args) {
        Map<String,String> map = new HashMap<String,String>();
        map.put("李杰","李英");
        map.put("黎晨辉","王成娟");
        map.put("蛮王","艾希");
        /*
        //map集合中遍历方式一: 使用keySet方法进行遍历       缺点: keySet方法只是返回了所有的键,没有值
        Set<String> keysView = map.keySet(); 
        System.out.println(keysView);
        
        //keySet() 把Map集合中的所有键都保存到一个Set类型 的集合对象中返回。
        Iterator<String> it = keysView.iterator();
        while(it.hasNext()) {
            //System.out.println(it.next());
            String list = it.next();
            System.out.print("{键:"+list+",值:"+map.get(list)+"}");
            System.out.println();
        }
        
        //map集合的遍历方式二: 使用values方法进行 遍历    缺点: values方法只能返回所有 的值,没有键
        Collection<String> valuesView = map.values();
        System.out.println(valuesView);
        Iterator<String> ir = valuesView.iterator();
        while(ir.hasNext()) {
            System.out.print(ir.next()+"   ");
        }
        */
        //map集合的遍历方式三: entrySet方法遍历
        Set<Map.Entry<String,String>> entrylist = map.entrySet();
        Iterator<Map.Entry<String,String>> io = entrylist.iterator();
        while(io.hasNext()){
            Map.Entry<String,String> entry = io.next();
            System.out.println("键:"+ entry.getKey()+" 值:"+ entry.getValue());
        }
    }
}

HashMap和TreeMap和Hashtable(了解)

  HashMap  底层也是基于哈希表实现 的。
    HashMap的存储原理:
       往HashMap添加元素的时候,首先会调用键的hashCode方法得到元素 的哈希码值,然后经过运算就可以算出该
       元素在哈希表中的存储位置
       情况1: 如果算出的位置目前没有任何元素存储,那么该元素可以直接添加到哈希表中


       情况2:如果算出 的位置目前已经存在其他的元素,那么还会调用该元素的equals方法与这个位置上的元素进行比较
       ,如果equals方法返回 的是false,那么该元素允许被存储,如果equals方法返回的是true,那么该元素被视为
       重复元素,不允存储

import java.util.HashMap;

class person{
     int id;
     String name;
     
     public person(int id, String name) {
            super();
            this.id = id;
            this.name = name;
     }
     
    public String toString() {
        return  "[编号:"+this.id+" 姓名:"+ this.name+"]";
    }
    
    @Override
    public int hashCode() {
        // TODO Auto-generated method stub
        return this.id;
    }
    @Override
    public boolean equals(Object obj) {
        person p = (person) obj;
        // TODO Auto-generated method stub
        return this.id == p.id;
    }
}

public class Demo3 {
    public static void main(String[] args) {
        HashMap<person,String> map = new HashMap<person,String>();
        map.put(new person(110,"李杰"), "lalala");
        map.put(new person(120,"李英"), "hahaha");
        map.put(new person(119,"李汉斯"), "xixixi");
        map.put(new person(119,"李汉斯"), "qiqiqi");
        System.out.println(map);
    }    
}

  TreeMap  TreeMap也是基于红黑树(二叉树)数据结构实现的    特点:会对元素的键进行排序存储

    TreeMap 要注意的事项:
       1.往TreeMap添加元素的时候,如果元素的键具备自然顺序,那么就会按照键的自然顺序特性进行排序存储
       2.往TreeMap添加元素的时候,如果元素的键不具备自然顺序特性, 那么键所属的类必须要实现Comparable接口,把键
        的比较规则定义在CompareTo方法上

       3. 往TreeMap添加元素的时候,如果元素的键不具备自然顺序特性,而且键所属的类也没有实现Comparable接口,那么就必须
          在创建TreeMap对象的时候传入比较器
 

import java.util.Comparator;
import java.util.TreeMap;

class Person {
    String name;
    int salary;
    public Person( String name,int salary) {
        super();
        this.name = name;
        this.salary = salary;
    }
    @Override
    public String toString() {
        return "[姓名:"+this.name+" 薪水:"+ this.salary+"]";
    }    
}

class mycompare implements Comparator<Person>{

    @Override
    public int compare(Person o1, Person o2) {
        // TODO Auto-generated method stub
        return o1.salary - o2.salary;
    }
    
}

public class Demo3 {
    public static void main(String[] args) {
        
        /*TreeMap<Character, Integer> tree = new TreeMap<Character, Integer>();
        tree.put('c',10);
        tree.put('b',2);
        tree.put('a',5);
        tree.put('h',12);
        System.out.println(tree);*/
        TreeMap<Person,Integer> tree = new TreeMap<Person,Integer>(new mycompare());
        tree.put(new Person("李杰",110), 001);
        tree.put(new Person("李英",120), 002);
        tree.put(new Person("李汉斯",119), 003);
        System.out.println(tree);        
        
    }
}
import java.util.Comparator;
import java.util.TreeMap;

class Person implements Comparable{
    String name;
    int salary;
    public Person( String name,int salary) {
        super();
        this.name = name;
        this.salary = salary;
    }
    @Override
    public String toString() {
        return "[姓名:"+this.name+" 薪水:"+ this.salary+"]";
    }
    
    @Override
    public int compareTo(Object o) {
        Person a = (Person) o;
        return this.salary - a.salary;
    }
    
}

public class Demo3 {
    public static void main(String[] args) {
        
        /*TreeMap<Character, Integer> tree = new TreeMap<Character, Integer>();
        tree.put('c',10);
        tree.put('b',2);
        tree.put('a',5);
        tree.put('h',12);
        System.out.println(tree);*/
        TreeMap<Person,Integer> tree = new TreeMap<Person,Integer>();
        tree.put(new Person("李杰",110), 001);
        tree.put(new Person("李英",120), 002);
        tree.put(new Person("李汉斯",119), 003);
        System.out.println(tree);        
        
    }
}

作业: 定义一个TreeMap,键存储的是书对象,值存储的是字符串。 根据书的出版出版日期排序

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.TreeMap;

class Book<T> implements Comparable<Book>{
    
    String name;
    String date; 
    public Book(String name,String string) {
        super();
        this.name = name;
        this.date = string;
    }
    /*
    @Override
    public int compareTo(Book o) {
        
        return this.date.compareTo(o.date);
    }
    */
    public int compareTo(Book o) {
        SimpleDateFormat dataformat = new SimpleDateFormat("yyyy-mm-dd");
        Date date1 = null;
        Date date2 = null;
        try {
            date1 = dataformat.parse(this.date);
            date2 = dataformat.parse(o.date);
        } catch (ParseException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    
        return date1.compareTo(date2);
    }
    @Override
    public String toString() {
        // TODO Auto-generated method stub
        return "{书名:"+this.name+"出版日期:"+this.date+",出版社:}";
    }
}

public class Demo4 {
    
    public static void main(String[] args) {
        TreeMap<Book, String>  map = new TreeMap<Book, String>();  //值存储书名
        map.put(new Book("《红楼梦》","2018-7-25"), "商务出版社");
        map.put(new Book("《西游记》","2018-7-26"), "商务出版社");
        map.put(new Book("《水浒传》","2018-7-27"), "商务出版社");
        map.put(new Book("《三国演义》","2018-7-28"), "商务出版社");
        System.out.println(map);
    }

}

HashTable  底层依赖哈希表存在的,实现方式与HashMap一直,但是他是线程安全的,操作效率低



原文地址:https://www.cnblogs.com/JYDesigner/p/9365891.html