Java基础--HashMap面试题

Posted mxh-java

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Java基础--HashMap面试题相关的知识,希望对你有一定的参考价值。

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * HashMap问题
 * @author 15735400536
 * 使用HashMap,如果key是自定义的类,就必须重写hashcode()和equals()
 * 使用ArrayList,如果元素是自定义的类,要做相等判断,就必须重写hashCode()和equals()
 */
public class HashMapTest 
	
	public static void main(String[] args) 
		Map<User,Doc> hashMap = new HashMap<User,Doc>();
		
		hashMap.put(new User("mxh","mxh"), new Doc("mxh","mxh"));
		hashMap.put(new User("root","root"), new Doc("root","root"));
		hashMap.put(new User("admin","admin"), new Doc("admin","admin"));
		
		//再不重写hashCode方法和equals方法的情况下get()方法拿到的结果为null
		//原因: new一个新的对象时,地址变了,不能保证hash值和equals结果还是一样。所以取不到对应的value。
		Object object = hashMap.get(new User("admin","admin"));
		System.out.println(object);
		
		List<Doc> list = new ArrayList<Doc>();
		list.add(new Doc("三国演义","罗贯中"));
		list.add(new Doc("红楼梦","曹雪芹"));
		list.add(new Doc("水浒传","施耐庵"));
		list.add(new Doc("西游记","吴承恩"));
		
		//Doc类未重写hashCode()和equals()方法前,结果为false
		boolean result = list.contains(new Doc("水浒传","施耐庵"));
		System.out.println("list集合是否存在该元素: " + result);
	


/**
 * 用户
 * @author 15735400536
 *
 */
class User 
	private String username;
	private String password;
	public String getUsername() 
		return username;
	
	public void setUsername(String username) 
		this.username = username;
	
	public String getPassword() 
		return password;
	
	public void setPassword(String password) 
		this.password = password;
	
	public User(String username, String password) 
		super();
		this.username = username;
		this.password = password;
	
	@Override
	public int hashCode() 
		final int prime = 31;
		int result = 1;
		result = prime * result + ((password == null) ? 0 : password.hashCode());
		result = prime * result + ((username == null) ? 0 : username.hashCode());
		return result;
	
	@Override
	public boolean equals(Object obj) 
		if (this == obj)
			return true;
		if (obj == null)
			return false;
		if (getClass() != obj.getClass())
			return false;
		User other = (User) obj;
		if (password == null) 
			if (other.password != null)
				return false;
		 else if (!password.equals(other.password))
			return false;
		if (username == null) 
			if (other.username != null)
				return false;
		 else if (!username.equals(other.username))
			return false;
		return true;
	
	


/**
 * 文档
 * @author 15735400536
 *
 */
class Doc 
	private String title;
	private String content;
	public String getTitle() 
		return title;
	
	public void setTitle(String title) 
		this.title = title;
	
	public String getContent() 
		return content;
	
	public void setContent(String content) 
		this.content = content;
	
	public Doc(String title, String content) 
		super();
		this.title = title;
		this.content = content;
	
	@Override
	public String toString() 
		return "Doc [title=" + title + ", content=" + content + "]";
	
	@Override
	public int hashCode() 
		final int prime = 31;
		int result = 1;
		result = prime * result + ((content == null) ? 0 : content.hashCode());
		result = prime * result + ((title == null) ? 0 : title.hashCode());
		return result;
	
	@Override
	public boolean equals(Object obj) 
		if (this == obj)
			return true;
		if (obj == null)
			return false;
		if (getClass() != obj.getClass())
			return false;
		Doc other = (Doc) obj;
		if (content == null) 
			if (other.content != null)
				return false;
		 else if (!content.equals(other.content))
			return false;
		if (title == null) 
			if (other.title != null)
				return false;
		 else if (!title.equals(other.title))
			return false;
		return true;
	


  1.hashcode()和equals()是在哪里被用到的?什么用的?

  HashMap是基于散列函数,以数组和链表的方式实现的。而对于每一个对象,通过其hashCode()方法可为其生成一个整形值(散列码),该整型值被处理后,将会作为数组下标,存放该对象所对应的Entry(存放该对象及其对应值)。equals()方法则是在HashMap中插入值或查询时会使用到。当HashMap中插入 值或查询值对应的散列码与数组中的散列码相等时,则会通过equals方法比较key值是否相等,所以想以自建对象作为HashMap的key,必须重写 该对象继承object的equals方法。

  2.本来不就有hashcode()和equals()了么?干嘛要重写,直接用原来的不行么?

  HashMap中,如果要比较key是否相等,要同时使用这两个函数!因为自定义的类的hashcode()方法继承于Object类,其hashcode码为默认的内存地址,这样即便有相同含义的两个对象,比较也是不相等的。

  Doc doc1 = new Doc("三国演义","罗贯中");
  Doc doc2 = new Doc("三国演义","罗贯中");

  正常理解这两个对象存入到hashMap中应该是相等的,但如果你不重写 hashcode()方法的话,比较是其地址,不相等!

  HashMap中的比较key是这样的,先求出key的hashcode(),比较其值是否相等,若相等再比较equals(),若相等则认为他们是相等 的。若equals()不相等则认为他们不相等。如果只重写hashcode()不重写equals()方法,当比较equals()时只是看他们是否为 同一对象(即进行内存地址的比较),所以必定要两个方法一起重写。HashMap用来判断key是否相等的方法,其实是调用了HashSet判断加入元素 是否相等。

以上是关于Java基础--HashMap面试题的主要内容,如果未能解决你的问题,请参考以下文章

java面试题基础

Java基础面试题

(小奇JAVA面试)每日10道Java面试题打卡—Java基础篇2

(小奇JAVA面试)每日10道Java面试题打卡—Java基础篇2

(小奇JAVA面试)每日10道Java面试题打卡—Java基础篇2

Java基础面试题