zoukankan      html  css  js  c++  java
  • 016.day16 HashSet TreeSet 比较器Comparable Comparator

    day16笔记

    一、HashSet

    1. 存储特点

    以hashCode排序,不能出现重复元素,相对无序(与输入顺序不相关)

    2. 比较规则

    首先比较hashCode,相同时调用当前对象的equals方法

    • 如果hashCode相同,equals方法比较不相同,则存储地址发生冲突,顺次后延
    • 如果hashCode相同,equals方法比较相同则为相同元素,不会添加
    • 如果hashCode不同,认定是不同对象,不会调用equals方法比较

    3. 哈希结构

    • 在Object中调用native声明的方法计算出一个与内存地址相关的编码
    • 可以在Object的子类中(所有类)重写hashCode方法
    • 通常重写hashCode时将其转换为和对象属性值相关的计算公式
    • 默认的hashCode计算方式使用31作为运算基数主要是出于性能的考虑

    二、TreeSet

    1. 存储特点

    以元素之间的比较结果决定存放的顺序,不能出现重复元素,默认按照自然升序

    2. 比较规则

    • 可以盛放实现了自然排序接口的实例,如:基本数据类型包装类,字符串,自定义类型等

    • 当一个TreeSet集合中出现不同类型的元素时,即泛型约束不强烈时,对于每一种类型均要实现自然排序接口,在重写的方法中指定不同类型比较时的结果,例如使用instanceof关键字判断比较对象的实例类型

      		Student student = null;
      		// 1.判断实例的类型
      		if (o instanceof Student) {
      			student = (Student) o;
      		}else {
      			// 如果待比较元素不是Student类型,不予添加
      			return 0;
      		}
      
    • 由于无法改写字符串及包装类中的compareTo方法,所以应避免在TreeSet集合中存入不兼容类型的数据

    • compareTo方法中,使用this关键字代表当前存入集合中的对象,参数列表中的对象为集合中已存在的对象,在得出最终比较结果时可能会发生多次比较

    • 基于二分法的比较规则,逐渐缩小所在元素应在区间

    • 返回0代表标记当前元素为重复元素,不会存入集合

    • 返回正数代表当前元素所处位置应在当前比较元素之后

    • 返回负数代表当前元素所处位置应在当前比较元素之前

    3.几个方法

    		TreeSet<Integer> treeSet = new TreeSet<>();
    		// 排序的时间:添加元素时,通过元素本身值的比较决定相应的属性,compareTo()方法调用
    		treeSet.add(50);
    		treeSet.add(30);
    		treeSet.add(100);
    		treeSet.add(20);
    		// 输出 20 30 50 100
    // treeSet.headSet()
    		// 第一个参数为指定的比较基准,不需要是集合中的元素(不包括参数这个元素)
    		for (Integer integer : treeSet.headSet(55)) {
    			System.out.println(integer); // 20 30 50 (55之前的元素)
    		}
    // treeSet.tailSet(比较的范围,是否包含-true)
    		// 第一个参数为指定的比较基准,不需要是集合中的元素(包括参数这个元素)
    		for (Integer integer : treeSet.tailSet(80)) {
    			System.out.println(integer);// 100 (80之后的元素)
    		}
    // treeSet.subSet(起始值,是否包含-true,终止值,是否包含-false)
    		// 第一个参数为指定的比较基准,不需要是集合中的元素
    		for (Integer integer : treeSet.subSet(20, 40)) {
    			System.out.println(integer);//20 30 (左闭右开)
    		}
    

    三、比较器

    1. Comparable

    自然排序接口,重写compareTo方法,使用方法见TreeSet

    // 1.实现comparable方法
    public class Student implements Comparable<Student>{}
    // 2.重写compareTo方法
    @Override
    	public int compareTo(Student o) {}
    //return 0 相同元素不存进去
    //return 1;// 正数放后
    //return -1;// 负数放前
    

    2. Comparator

    外部排序接口,使用匿名内部类的方式实现,指定泛型,并重写compare(paraA,paraB)方法

    // 匿名内部类 -> 只能使用一次,不需要更改类本身的结构,比较规则有变动的情况
    		// 当同时具有Comparable和Comparator时,以Comparator规则为准
    		Set<Person> set = new TreeSet<>(new Comparator<Person>() {
                // 需求:向TreeSet集合当中存放Student对象,使得对象之间根据年龄升序
    			@Override
    			public int compare(Person newPerson, Person oldPerson) {
                // 第一个参数为新添加进来的对象,第二个参数为集合当中与之比较的对象
    				// 当两个对象属性完全相同时,认定是重复对象,返回0
    				if (newPerson.getName().equals(oldPerson.getName()) && newPerson.getAge() == oldPerson.getAge()) {
    					// 当两个比较对象各属性相同时,认定相同,不予添加
    					return 0;
    				}
    				// 2.年龄的比较
    				if (newPerson.getAge() >= oldPerson.getAge()) {
    					// 通过正负来决定位置
    					// 正数放后
    					// 负数放前
    					return 1;
    				} else {
    					return -1;
    				}
    			}
    		});
    
    • paraA代表当前正在存入的元素
    • paraB代表集合中已存在的元素,有可能发生多次比较
    • 返回0代表标记当前元素为重复元素,不会存入集合
    • 返回正数代表当前元素所处位置应在当前比较元素之后
    • 返回负数代表当前元素所处位置应在当前比较元素之前
  • 相关阅读:
    Linux基础知识[1]【ACL权限】
    docker 入门学习篇【基本命令与操作】
    centos7.1下 Docker环境搭建
    RHEL6.5下更新python至2.7版本
    Github初学者探索
    vmware下linux虚拟机传文件解决方案之 xftp
    mysql 常用操作命令
    常用DNS记录
    常见网络协议端口号整理
    DNS原理及其解析过程 精彩剖析
  • 原文地址:https://www.cnblogs.com/yokii/p/9417431.html
Copyright © 2011-2022 走看看