码迷,mamicode.com
首页 > 其他好文 > 详细

集合最后一章 HashMap Hashtable Properties 自平衡二叉树 集合工具类 以及总结各个集合

时间:2021-06-02 18:58:20      阅读:0      评论:0      收藏:0      [点我收藏+]

标签:http   单向链表   package   container   技术   ati   面试   containe   alt   

技术图片

重写hashCode和equals

(1)向Map集合中存,以及从Map集合中取,都是先调用key的hashCode方法,然后调用equals方法!

equals方法有可能调用,也有可能不调用

 

往里面存的时候会先调用Hashcode方法,得到Hash值

  • 拿put(k,v)举例,什么时候equals不会调用?

    k.HashCode()方法返回哈希值

    哈希值经过哈希算法转换成数组下标。

    数组下标位置上如果是null,equals不需要执行

  • 拿get(k)举例,什么时候equals方法不会调用?

    k.hashCode()方法返回哈希值

    哈希值经过哈希算法转换成数组下标。

    数组下标位置上如果是null,equals不需要执行

    (2)注意: 如果一个类的equals方法重写了。那么hashCode方法()也必须重写

    并且equals方法返回如果是true。hashCode()方法返回值必须一样

    • equals方法返回true,表示两个对象相同,在同一个单向链表上比较,那么对于同一个单向链表上的节点来说,他们的哈希值都是相同的。

    • 所以hashCode()方法的返回值也应该相同

       

(3)HashCode和equals方法直接用idea生成。

(4)终极结论:

            放在HashMap集合key部分的,以及放在HashSet集合中的元素,需要同时重写hashCode方法和equals方法

HashMap (非线程安全的)

  • 初始化容量16 默认加载因子 .75

  • 扩容是:扩容之后的容量是原容量的2倍

在jdk8之后如果单向链表中元素超过8个,单项链表这种数据结构会变成红黑树数据结构。当红黑树上的节点数量小于6时,会重新把红黑树变成单项链表数据结构

这种方式也是为了提高检索效率,二叉树的检索会再次缩小扫描范围,提高效率

Hashtable (线程安全的)

技术图片

hash值相同的话。一定在同一个链表上。

(5)对于哈希表数据结构来说:

如果o1和o2的哈希值相同。一定是放到同一个单向链表上

当然如果o1和o2的hash值不同,但由于哈希算法执行结束之后转换的数组下标可能相同,此时会发生“哈希碰撞”

技术图片

结果相同、


HashMap集合key部分允许null吗?

允许

但是要注意:HashMap集合的key null值只能有一个。

有可能面试会遇到这样的问题

技术图片


Hashtable的key可以是null吗?

Hashtable的key和value都不可以是null

HashMap集合的key和value都可以是null

Hashtable方法都带有synchronized:线程安全的。

线程安全有其他的方案;这个Hashtable对线程的处理导致效率较低,使用较少了

Hashtable和HashMap一样底层都是哈希表数据结构

 

Hashtable的初始容量是11

Hashtable集合扩容是 原容量*2+1

Properties

目前只需要掌握Properties属性类对象的相关方法即可

Properties是一个Map集合,继承Hashtable,Properties的key和value都是String类型

Properties被称为属性类对象

Properties是线程安全的

HashSet集合的初始化容量16

初始化容量建议是2的倍数

扩容:扩容之后是原容量的2倍

TreeSet

  • TreeSet集合底层实际上是一个TreeMap

  • TreeMap集合底层是一个二叉树

  • 放到TreeSet集合中的元素,等同于放到TreeMap 集合key部分了

  • TreeSet节中的元素:无序不可重复,但是可以按照元素的大小顺序自动排序

称为:可排序集合

?
public class TreeSetTest01 {
   public static void main(String[] args) {
       TreeSet <Integer>  ts =new TreeSet<>();
       ts.add( 13242);
       ts.add(232);
       ts.add( 23);
       for (Integer num : ts){
           System.out.println(num);
      }
?
  }
}
存进去取出来有序的
 

对自定义的类型可以排序吗?

不行

因为没有指定排序规则

技术图片

放在TreeSet集合中的元素需要实现java.lang.Comparable 接口

并实现compareTo方法 equals方法可以不写

技术图片

package com.zhangjunlong.some.some.some.some;
?
public class TreeSetTest02 {
   public void Customer(){
?
  }
   class Customer implements  Comparable<Customer>{
?
       @Override
       //写排序规则 按照什么进行比较
       public int compareTo(Customer o) {
           return this.age-o.age;
      }
       int age ;
       public Customer (int age ){
           this.age = age ;
      }
  }}
?

compareTo方法的返回值很重要

返回0 表示相同。value会覆盖

返回>0 会继续在右子树上找。

返回<0 会继续在左子树上找。

 

自平衡二叉树

  • 自平衡二叉树 遵循左小右大的原则存放

  • 遍历二叉树的时候有三种方法

    • 前序遍历:根左右

    • 中序遍历:左根有

    • 后序遍历 :左右根

    注意:

    前中后说的是“根”的位置

    根在前面就是前序 ,根在中间是中序, 根在后面试后序

  • TreeSet集合、TreeMap集合采用的是:中序遍历方式

Iterator迭代器采用的是中序遍历方式

左根右

  • 存放是要依靠左小右大原则,所以这个存放的时候要进行比较

  • 技术图片

  • 采用中序遍历取出:

    • 左根右 40 50 55 60 80 100 120 130 135 140 180 200 666

    •  


TreeSet集合中的元素可排序的第二种方式:使用比较器的方式

  • 单独在这个编写一个比较器

  • 比较器实现java . util.Comparator 接口 。(Comparable 是java.lang 包下的、Comparator是java.util包下的。)

       class WuGuiComparator  implements Comparator<Customer>{
           @Override
           public int compare(Customer o1, Customer o2) {
               return o1.getAge() - o2.getAge();
          }
      }
    ?

     

技术图片

主要传递一个比较器


也可以采取匿名内部类的方法(这个类没有名字。直接new接口)

技术图片

最终结论

放到TreeSet或者TreeMap集合key 部分的元素要想做到排序,包括两种方式:

  • 放到集合中的元素实现java . lang .Comparable接口

  • 在构造TreeSet或者TreeMap集合的时候给它传一个比较器对象

Comparable和Comparator怎么选择

当比较规则不会发生改变的时候,或者说当比较规则只要1个的时候,建议实现Comparable接口

如果比较规则有多个,并且需要多个比较规则之间频繁切换,建议使用Comparator接口

 

Comparator接口的设计符合OCP原则

OCP : open closed principle : 开闭原则 对扩展开放 对修改关闭

集合工具类

java.util.Collection 集合接口

java.util.Collections 集合工具类,方便集合的操作

 

package com.zhangjunlong.some.some.some.some;
?
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
?
?
public class CollectionsTest {
   public static void main(String[] args) {
//ArrayList集合不是线程安全的
       List <String> list =new ArrayList<>();
       Collections.synchronizedList(list);
       //   变成线程安全的
?
       // 排序
       list .add( "2342");
       list.add("zhasdf");
       list.add("234xscfs");
       Collections.sort(list);
       for (String s : list){
           System.out.println(s);
      }
?
?
  }
}
?

注意:对list集合中元素进行排序,需要保证list集合中元素实现了:Comparable接口

Collections.synchronizedList(list);

变成线程安全de

Collections.sort(list);

进行排序

List<String >mylist  =new ArrayList <>(set);
将Set集合转换成List集合
   

 

技术图片

 

 

总结 集合

  • 集合这块最主要掌握什么内容

    • 每个集合对象的创建(new)

    • 向集合中添加元素

    • 从集合中取出某个元素

    • 遍历集合

    • 主要的集合类

      • ArrayList

      • LinkList

      • HashSet(HashMap的key,存储在HashMap集合key的元素需要同时重写hashCode+equals)

      • TreeSet

      • HashMap

      • Properties

      • TreeMap

ArrayList

技术图片

技术图片

 

linkedList与ArrayList集合相似

HashSet(无序不可重复)

set集合中的元素 不能通过下标取了,没有下标

技术图片

集合的构造方法完成集合的转换

TreeSet(可排序的)

技术图片

编写比较器,可以改变 规则

技术图片

技术图片

HashMap

key重复 value会覆盖

技术图片

遍历 Map集合很重要

几种方式都要会

第一种:先获取key ,遍历key。通过key获取value

map.keySet ()

技术图片

第二种:是将Map集合转换成set集合,Set集合中每一个元素都是Node

这个Node节点中有key 和value、

技术图片

Properties

技术图片

package com.zhangjunlong.some.some.some.some;
?
import java.util.Properties;
?
public class PrppertiesTest {
   public static void main(String[] args) {
       Properties properties =new Properties();
       properties.setProperty("userName","zhangsan");
       properties.setProperty("userNum","12312543245345");
       String name = properties.getProperty("userName");
       System.out.println(name);
?
  }
}
?

 

集合最后一章 HashMap Hashtable Properties 自平衡二叉树 集合工具类 以及总结各个集合

标签:http   单向链表   package   container   技术   ati   面试   containe   alt   

原文地址:https://www.cnblogs.com/geren/p/14832353.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!