• 什么是HashSet?

    • 它实现了Set接口,HashSet是Set集合的子类
    • 有哈希表支持的,元素不可重复的哈希码值(实际上是一个HashMap的实例).
    • 它不保证set的迭代顺序(遍历元素的顺序),遍历元素的顺序和存储元素的顺序不一致.
    • 允许使用null元素.HashSet,范型的确定类型必须是引用数据类型,引用数据类型的默认初值就是null

    总结:无序,可为null,不可重复(由哈希码表支持),实质是一个hashMap

public static void main( String[] args )
{
//需求1:arrayList中有存放学生类,有学生张三\张三\李四,去重张三
//创建另一个集合,通过对比实体,来去重
List<Student> oldStu = new ArrayList<>();
oldStu.add(new Student(1,"张三"));
oldStu.add(new Student(1,"张三"));
oldStu.add(new Student(2,"李四")); List<Student> newStu = new ArrayList<>();
oldStu.forEach((stu) -> {
if (!newStu.contains(stu)){
newStu.add(stu);
}
}); System.out.println(newStu);
/**
* 打印结果:[Student{id=1, name='张三'}, Student{id=1, name='张三'}, Student{id=2, name='李四'}]
* 没有去重,原因:contains比较的是实体的equals方法 ----> if (o.equals(elementData[i])),同时对象类型是Object类型,
* 所以比较的是对象的hashcode值.而每一次new 对象都会生成一个新的hash地址值,所以无法判断实体的内容是否相等.
*
* //contains
* public boolean contains(Object o) {
* return indexOf(o) >= 0;
* }
*
* //indexOf
* public int indexOf(Object o) {
* if (o == null) {
* for (int i = 0; i < size; i++)
* if (elementData[i]==null)
* return i;
* } else {
* for (int i = 0; i < size; i++)
* if (o.equals(elementData[i]))
* return i;
* }
* return -1;
* }
*/ //需求2:HashSet中有存放学生类,有学生张三\张三\李四,去重张三
Set<Person> personSet = new HashSet<>();
personSet.add(new Person(1,"张三"));
personSet.add(new Person(1,"张三"));
personSet.add(new Person(2,"李四")); System.out.println(personSet);
/**
* 1.打印结果:[Person{id=1, name='张三'}, Person{id=2, name='李四'}, Person{id=1, name='张三'}]
* 没有去重,原因还是因为对象的hashCode()方法,因为在存放的时候,同样是存放的范型对象,每一个对象的创建都会
* 在堆中申请新的内存空间,也就是默认调用了一次hashCode(),所以第一次add和第二次add,存放的本身就是不同的,所以没有去重.
* 如何实现呢?
* 同样的重写对象的hashCode()方法和equals()方法,以保证实体的去重
* 2.打印结果:[Person{id=2, name='李四'}, Person{id=1, name='张三'}]
*
* public boolean add(E e) {
* return map.put(e, PRESENT)==null;
* }
*/ }
class Person{

    private Integer id;
private String name; public Person() {
} public Person(Integer id, String name) {
this.id = id;
this.name = name;
} public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} @Override
public String toString() {
return "Person{" +
"id=" + id +
", name='" + name + '\'' +
'}';
} @Override
public boolean equals(Object o) {
if (this == o) return true;
if (!(o instanceof Person)) return false;
Person person = (Person) o;
return Objects.equals(id, person.id) &&
Objects.equals(name, person.name);
} @Override
public int hashCode() {
return Objects.hash(id, name);
}
}
class Student{
private Integer id;
private String name; public Student() {
} public Student(Integer id, String name) {
this.id = id;
this.name = name;
} public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
} @Override
public String toString() {
return "Student{" +
"id=" + id +
", name='" + name + '\'' +
'}';
} //改进:重写equals方法,比较实体的内容
//打印结果:[Student{id=1, name='张三'}, Student{id=2, name='李四'}]
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (!(o instanceof Student)) return false;
Student student = (Student) o;
return Objects.equals(id, student.id) &&
Objects.equals(name, student.name);
} @Override
public int hashCode() {
return Objects.hash(id, name);
}
}

HashMap初认识的更多相关文章

  1. Java中HashSet,HashMap和HashTable的区别

    HashMap.HashSet.HashTable之间的区别是Java程序员的一个常见面试题目,在此仅以此博客记录,并深入源代码进行分析: 在分析之前,先将其区别列于下面 1:HashSet底层采用的 ...

  2. [置顶] HashMap HashTable HashSet区别剖析

    HashMap.HashSet.HashTable之间的区别是Java程序员的一个常见面试题目,在此仅以此博客记录,并深入源代码进行分析: 在分析之前,先将其区别列于下面 1:HashSet底层采用的 ...

  3. 初建FreeMarker工程

    初建FreeMarker工程 ——@梁WP 背景:听说freemarker可以用来写页面的组件,热衷于编写可重用代码的我,迫不及待地研究了freemarker,不过,在写组件之前,还是先研究一下fre ...

  4. HashMap HashTable HashSet区别剖析

    HashMap.HashSet.HashTable之间的区别是Java程序员的一个常见面试题目,在此仅以此博客记录,并深入源代码进行分析: 在分析之前,先将其区别列于下面 1:HashSet底层采用的 ...

  5. HashMap为什么线程不安全(hash碰撞与扩容导致)

    一直以来都知道HashMap是线程不安全的,但是到底为什么线程不安全,在多线程操作情况下什么时候线程不安全? 让我们先来了解一下HashMap的底层存储结构,HashMap底层是一个Entry数组,一 ...

  6. HashMap 源码详细分析(JDK1.8)

    一.概述 本篇文章我们来聊聊大家日常开发中常用的一个集合类 - HashMap.HashMap 最早出现在 JDK 1.2中,底层基于散列算法实现.HashMap 允许 null 键和 null 值, ...

  7. HashTable & HashMap & ConcurrentHashMap 原理与区别

    一.三者的区别     HashTable HashMap ConcurrentHashMap 底层数据结构 数组+链表 数组+链表 数组+链表 key可为空 否 是 否 value可为空 否 是 否 ...

  8. 六.HashMap HashTable HashSet区别剖析总结

    HashMap.HashSet.HashTable之间的区别是Java程序员的一个常见面试题目,在此仅以此博客记录,并深入源代码进行分析: 在分析之前,先将其区别列于下面: 1.HashSet底层采用 ...

  9. 【不做标题党,只做纯干货】HashMap在jdk1.7和1.8中的实现

     同步首发:http://www.yuanrengu.com/index.php/20181106.html Java集合类的源码是深入学习Java非常好的素材,源码里很多优雅的写法和思路,会让人叹为 ...

随机推荐

  1. ArrayAdapter、SimpleAdapter简单用法

    1. 使用流程 2. ArrayAdapter new ArrayAdapter<?>(context, textViewResourceId, objects)   context:上下 ...

  2. 从头认识一下docker-附带asp.net core程序的docker化部署

    从头认识一下docker-附带asp.net core程序的docker化部署 简介 在计算机技术日新月异的今天, Docker 在国内发展的如火如荼,特别是在一线互联网公司, Docker 的使用是 ...

  3. matlab练习程序(水波特效)

    还记得原来写过一个对图像进行波纹扭曲操作的博文. 这次实现的是水波特效,其实就是通过正余弦函数表示波纹中心位置慢慢向外扩散,通过叠加衰减因子使振幅不断减小,进而产生水波的效果. 效果如下: 原图: 波 ...

  4. nginx配置静态项目

    当nignx可以加载下面的这个service时 server { listen 8085;  server_name 1.192.60.82; location / { root /etc/nginx ...

  5. mysql免安装版初次使用

    在自己电脑上安装一个mysql数据库并启动,碰到一些问题,总结一下 1.下载免安装版mysql数据库,百度下载了了5.7.25版本 2.在bin文件夹下找到my-defaults.ini文件,我这没有 ...

  6. 【原】Java学习笔记023 - 字符串缓冲区_正则表达式

    package cn.temptation; import java.util.Arrays; public class Sample01 { public static void main(Stri ...

  7. 伙伴系统之伙伴系统概述--Linux内存管理(十五)

    在内核初始化完成之后, 内存管理的责任就由伙伴系统来承担. 伙伴系统基于一种相对简单然而令人吃惊的强大算法. Linux内核使用二进制伙伴算法来管理和分配物理内存页面, 该算法由Knowlton设计, ...

  8. 【PAT】B1014 福尔摩斯的约会

    因为前面两字符串中第 1 对相同的大写英文字母(大小写有区分)是第 4 个字母D,代表星期四: 第 2 对相同的字符是 E ,那是第 5 个英文字母,代表一天里的第 14 个钟头(于是一天的 0 点到 ...

  9. Idea+Maven创建scala项目

    1.选择Create New Project 2.如下图选择,然后下一步 3.一直Next,填写groupID,artifactid,projectName之后等待IDEA初始化. 4.IDEA完成初 ...

  10. Java 8 新特性7-方法引用、继承

    (原) 方法引用: 方法引用有4种: 1.静态方法引用:类名::静态方法名 在java中,对集合的排序,我们常用java提供的 Collections.sort(List<T> list, ...