lesson10:hashmap变慢原因分析
下面的英文描述了String.hashCode()方法,在特定情况下,返回值为0的问题:
Java offers the HashMap and Hashtable classes, which use the
String.hashCode() hash function. It is very similar to DJBX33A (instead of 33, it uses the
multiplication constant 31 and instead of the start value 5381 it uses 0). Thus it is also
vulnerable to an equivalent substring attack. When hashing a string, Java also caches the
hash value in the hash attribute, but only if the result is different from zero.
Thus, the target value zero is particularly interesting for an attacker as it prevents caching
and forces re-hashing.
接下来我们来看一下String类的hashCode()方法:当下面代码中的val[off++]返回值都是0的情况下,hashCode()的返回值也是0
public int hashCode() {
int h = hash;//初始值为0
if (h == 0 && count > 0) {//count值为字符个数
int off = offset;//off值为0
char val[] = value;//字符数组
int len = count; for (int i = 0; i < len; i++) {
h = 31*h + val[off++];//如果val[off++]的所有返回值都是ascii码0会发生什么?
}
hash = h;
}
return h;
}
我们知道hashmap存储值的数据结构是数组+链表的结果,如果不同的key值,但是返回的hashcode()值都是0的话,hashmap的结构不会得到很好的应用,会造成所有的元素都存储在数组的第一个元素的链表中,下面通过代码来证明:
package com.mantu.advance; import java.util.HashMap; public class Lesson10HashmapLeak { public static void main(String[] args){
testHashMapNormal();
testHashMapBug();
} public static void testHashMapBug(){
HashMap<String,String> map = new HashMap<String,String>(100000);
String xxx= asciiToString("0");
String temp = xxx;
long beginTime = System.currentTimeMillis();
//System.out.println("开始时间:"+System.currentTimeMillis());
for(int i=0;i<100000;i++){
map.put(xxx, i+""); if((i%10000)==0){
xxx=temp;
}
else{
xxx=xxx+temp;
}
}
System.out.println("testHashMapBug()耗时:"+(System.currentTimeMillis()-beginTime)+"毫秒");
} public static void testHashMapNormal(){
HashMap<String,String> map = new HashMap<String,String>(100000);
String xxx= asciiToString("1");
String temp = xxx;
long beginTime = System.currentTimeMillis();
//System.out.println("开始时间:"+System.currentTimeMillis());
for(int i=0;i<100000;i++){
map.put(xxx, i+""); if((i%10000)==0){
xxx=temp;
}
else{
xxx=xxx+temp;
}
}
System.out.println("testHashMapNormal()耗时:"+(System.currentTimeMillis()-beginTime)+"毫秒");
}
public static String asciiToString(String value)
{
StringBuffer sbu = new StringBuffer();
String[] chars = value.split(",");
for (int i = 0; i < chars.length; i++) {
sbu.append((char) Integer.parseInt(chars[i]));
}
return sbu.toString();
}
}
最后的执行结果是:
正常key值的一组执行时间是:1887毫秒
key值对应的hashcode()值为0的执行时间是:7365毫秒
lesson10:hashmap变慢原因分析的更多相关文章
- SELECT TOP 1 比不加TOP 1 慢的原因分析以及SELECT TOP 1语句执行计划预估原理
本文出处:http://www.cnblogs.com/wy123/p/6082338.html 现实中遇到过到这么一种情况: 在某些特殊场景下:进行查询的时候,加了TOP 1比不加TOP 1要慢(而 ...
- HashMap多线程并发问题分析
转载: HashMap多线程并发问题分析 并发问题的症状 多线程put后可能导致get死循环 从前我们的Java代码因为一些原因使用了HashMap这个东西,但是当时的程序是单线程的,一切都没有问题. ...
- Beforeunload打点丢失原因分析及解决方案
淘宝的鱼相在 2012 年 8 月份发表了一篇文章,里面讲述了他们通过一个月的数据采集试验,得到的结果是:如果在浏览器的本页面刷新之前发送打点请求,各浏览器都有不同程度的点击丢失情况,具体点击丢失率统 ...
- SQL Server 磁盘请求超时的833错误原因分析以及解决
本文出处:http://www.cnblogs.com/wy123/p/6984885.html 最近遇到一个SQL Server服务器响应极度缓慢,并且出现客户端请求报错的情况,在数据库中的erro ...
- SQL查询速度慢的原因分析和解决方案
SQL查询速度慢的原因分析和解决方案 查询速度慢的原因很多,常见如下几种: 1.没有索引或者没有用到索引(这是查询慢最常见的问题,是程序设计的缺陷) 2.I/O吞吐量小,形成了瓶颈效应. 3.没有创建 ...
- PHPWAMP自启异常,服务器重启后Apache等服务不会自动重启的原因分析
在使用“PHPWAMP自动任务”时,不少学生遇到如下问题: “phpwamp绿色集成环境重启动电脑(服务器)后,不会自动启动网站服务” (如果是其他环境或是自己搭建时遇到此问题,也是可以用此法解决) ...
- sql 查询慢的48个原因分析
sql 查询慢的48个原因分析. server memory 服务器配置选项配置为物理内存的 1.5 倍(虚拟内存大小设置的一半). 字句同时执行,SQL SERVER根据系统的负载情况决定最优的 ...
- ORACLE中order by造成分页不正确原因分析
工作中遇到的问题: 为调用方提供一个分页接口时,调用方一直反应有部分数据取不到,且取到的数据有重复的内容,于是我按以下步骤排查了下错误. 1.检查分页页码生成规则是否正确. 2.检查SQL语句是否正 ...
- Android ListView异步载入图片乱序问题,原因分析及解决方式
转载请注明出处:http://blog.csdn.net/guolin_blog/article/details/45586553 在Android全部系统自带的控件其中,ListView这个控件算是 ...
随机推荐
- SGU 224.Little Queens
时间限制:0.75s 空间限制:6M 题意 n*n(n<=10)的棋盘,求出放置m(m<=n*n)个皇后的方案数. Solution: 状态压缩+位运算 搜索. 首先我们从上往下逐行放置 ...
- 在easyui dialog的子页面内如何关闭弹窗
因项目需要在dialog中添加滚动条,所以就在div中加了iframe: <div id="applyRefundDialog" style="display:no ...
- C# winform 递归选中TreeView子节点
/// <summary> /// 递归选中所有的自节点 /// </summary> /// <param name="nodeThis">T ...
- Django Web在Apache上的部署
1. 安装配置Apache 2. 安装wsgi_mod模块 3. 开放相应端口 vim /etc/sysconfig/iptables # Firewall configuration written ...
- NameNode元数据的管理机制(三)
元数据的管理: 第一步:客户端通过DistributedFilesystem 对象中的creat()方法来创建文件,此时,RPC会 通过一个RPC链接协议来调用namenode,并在命名空间中创建一个 ...
- api1
http://www.android-doc.com/reference/android/app/Fragment.html
- IOS网络编程:HTTP
IOS网络编程:HTTP HTTP定义了一种在服务器和客户端之间传递数据的途径. URL定义了一种唯一标示资源在网络中位置的途径. REQUESTS 和 RESPONSES: 客户端先建立一个TCP连 ...
- Apache HTTPServer与JBoss/Tomcat的整合与请求分发
http://www.blogjava.net/supercrsky/archive/2008/12/24/248143.html
- 转:我终于离开了年薪30w的IT行业
题目乍看起来有点故意惹人眼球的味道,但是对于我事实就是如此,暂且请君听我细细道来! 先自曝家门,我03年毕业,05年来深,06年买车子,06年底结婚,07年买了房子,09年生了儿子,妻子.房 ...
- myisam和innodb索引实现的不同
1.MyISAM 使用B+Tree 作为索引结构,叶子节点的data存放指针,也就是记录的地址.对于主键索引和辅助索引都是一样的.2.InnoDB 也使用B+Tree作为索引结构,也别需要注意的是,对 ...