19.并发下的ArrayList、HashMap,Integer加锁问题
import java.util.ArrayList;
import java.util.Vector;
/**
* 并发下的ArrayList
*/
public class ArrayListMultiThread {
static ArrayList<Integer> arrayList = new ArrayList<>();
// static Vector<Integer> arrayList = new Vector<>(); //解决方式 使用线程安全的Vector代替ArrayList
public static class AddThread implements Runnable{
@Override
public void run() {
// synchronized (ArrayListMultiThread.class){ //解决方式加锁
for (int i = 0; i < 1000000; i++) {
arrayList.add(i);
}
// }
}
}
public static void main(String[] args) throws InterruptedException{
Thread thread1 = new Thread(new AddThread());
Thread thread2 = new Thread(new AddThread());
thread1.start();
thread2.start();
thread1.join();thread2.join();
System.out.println(arrayList.size());
//Exception in thread "Thread-1" java.lang.ArrayIndexOutOfBoundsException: 10
// at java.util.ArrayList.add(ArrayList.java:463)
// at com.combat.ArrayListMultiThread$AddThread.run(ArrayListMultiThread.java:11)
// at java.lang.Thread.run(Thread.java:748)
//1000001
//这种结果是因为ArrayList在扩容过程中,内部一致性被破坏,但由于没有锁的保护,另一个线程访问到了不一致的内部状态
//导致出现越界问题
//结果二:2000000
//结果二:小于2000000
}
}
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
/**
* 并发下的HashMap
* jdk8
*/
public class HashMapMultiThread {
static Map<String,String> map = new HashMap<>();
// static ConcurrentHashMap<String,String> map = new ConcurrentHashMap<>(); //解决方式 用ConcurrentHashMap代替HashMap
public static class AddThread implements Runnable{
int start = 0;
public AddThread(int start){
this.start = start;
}
@Override
public void run() {
// synchronized (HashMapMultiThread.class){ // 解决方式
for (int i = start; i < 100000; i+=2) {
map.put(Integer.toString(i),Integer.toBinaryString(i));
}
// }
}
}
public static void main(String[] args) throws InterruptedException{
Thread thread1 = new Thread(new AddThread(0));
Thread thread2 = new Thread(new AddThread(1));
thread1.start();
thread2.start();
thread1.join();
thread2.join();
System.out.println(map.size());
//Exception in thread "Thread-1" Exception in thread "Thread-0" java.lang.ClassCastException: java.util.HashMap$Node cannot be cast to java.util.HashMap$TreeNode
// at java.util.HashMap$TreeNode.moveRootToFront(HashMap.java:1832)
// at java.util.HashMap$TreeNode.treeify(HashMap.java:1949)
// at java.util.HashMap.treeifyBin(HashMap.java:772)
// at java.util.HashMap.putVal(HashMap.java:644)
// at java.util.HashMap.put(HashMap.java:612)
// at com.combat.HashMapMultiThread$AddThread.run(HashMapMultiThread.java:19)
// at java.lang.Thread.run(Thread.java:748)
//java.lang.ClassCastException: java.util.HashMap$Node cannot be cast to java.util.HashMap$TreeNode
// at java.util.HashMap$TreeNode.moveRootToFront(HashMap.java:1832)
// at java.util.HashMap$TreeNode.putTreeVal(HashMap.java:2012)
// at java.util.HashMap.putVal(HashMap.java:638)
// at java.util.HashMap.put(HashMap.java:612)
// at com.combat.HashMapMultiThread$AddThread.run(HashMapMultiThread.java:19)
// at java.lang.Thread.run(Thread.java:748)
//2778
// 结果二:小于100000
//JDk7会出现死循环 HashMap put()是一个迭代遍历,如同遍历链表一样,但由于多线程,链表成环了,形成死循环
}
}
/**
* Integer加锁
*/
public class BadLockOnInteger implements Runnable{
public static Integer i = 0;
static BadLockOnInteger instance = new BadLockOnInteger();
@Override
public void run() {
for (int j = 0; j < 10000000; j++) {
synchronized (i){
// synchronized (instance){ // 修改方式
i++; //相当于 i = Integer.valueOf(i.intValue()+1);
}
}
}
public static void main(String[] args) throws InterruptedException{
Thread thread1 = new Thread(instance);
Thread thread2 = new Thread(instance);
thread1.start();thread2.start();
thread1.join();thread2.join();
System.out.println(i);
//12968375 小于20000000
//java中Integer属于不变对象,一旦创建就不可能被修改
//i++的本质是创建一个新的Integer对象,并将他的引用赋值给i
//两个线程每次加锁可能都加在了不同的对象实例上
}
}
19.并发下的ArrayList、HashMap,Integer加锁问题的更多相关文章
- Junit + String/Integer/ArrayList/HashMap/TreeMap 基本使用Demo
package JavaTest.test; import java.util.ArrayList; import java.util.HashMap; import java.util.List; ...
- 2.8.3 并发下诡异的HashMap
package 第二章.并发下诡异的HashMap; import org.junit.Test; import java.util.HashMap;import java.util.Map;impo ...
- 2.8.2 并发下的ArrayList,以及源码分析
package 第二章.并发下的ArrayList; import java.util.ArrayList;import java.util.List; /** * Created by zzq on ...
- java 遍历方法 及 数组,ArrayList,HashMap,HashSet的遍历
一,遍历方法的实现原理 1.传统的for循环遍历,基于计数器的: 遍历者自己在集合外部维护一个计数器,然后依次读取每一个位置的元素,当读取到最后一个元素后,停止.主要就是需要按元素的位置来读取元素. ...
- HashMap<Integer, Bean> 根据Bean的属性进行排序
转载地址 已知一个HashMap<Integer,User>集合, User有name(String)和age(int)属性.请写一个方法实现对HashMap的排序功能,该方法接收Hash ...
- 性能优化:使用SparseArray代替HashMap<Integer,Object>(转)
HashMap是java里比较常用的一个集合类,我比较习惯用来缓存一些处理后的结果.最近在做一个Android项目,在代码中定义这样一个变量,实例化时,Eclipse却给出了一个 performanc ...
- Java基础知识强化之集合框架笔记55:Map集合之HashMap集合(HashMap<Integer,String>)的案例
1. HashMap集合(键是Integer,值是String的案例) 2. 代码示例: package cn.itcast_02; import java.util.HashMap; import ...
- 自己写的demo。List<HashMap<String,Object>>=new ArrayList<HashMap<String,Object>>
package com.pb.collection; import java.util.ArrayList; import java.util.HashMap; import java.util.It ...
- 将ArrayList<HashMap<String, String>>转为ArrayList<Bundle>类型的解决方案
Bundle是一种利用键值对存储的数据格式,而我们在程序中通常利用HashMap存储数据.在开发中,通过Http请求得到JSONArray类型的返回值,我选择利用ArrayList<HashMa ...
随机推荐
- mybatis整合redis二级缓存
mybatis默认开启了二级缓存功能,在mybatis主配置文件中,将cacheEnabled设置成false,则会关闭二级缓存功能 <settings> <!--二级缓存默认开启, ...
- JSP中获取客户端或浏览端信息的方式
request应用:在JSP页面显示访问者IP 方式一:纯前台,不涉及后台操作.直接在jsp页面中需要显示IP的地方使用 代码:<%=request.getRemoteAddr()%> ...
- Docker(应用服务引擎)
Docker 是一个开源的应用容器引擎,让开发者可以打包他们的应用以及依赖包到一个可移植的容器中,然后发布到任何流行的 Linux 机器上,也可以实现虚拟化.容器是完全使用沙箱机制,相互之间不会有任何 ...
- vue项目打包之后原本好的样式变得不好了的原因分析
这个主要是打包的过程将所有的css文件进行归类压缩,导致原先其他文件里的样式对当前的产生了影响,应该有同样的类名了.怎么改?要么改类名,要么用scope,scss的写法.
- vue多个input绑定一个数组变量问题
对于data中声明的一个数组变量arr=[],在绑定时候可以如下: <div style="margin-top: 10px;margin-left: 40px;"> ...
- 原生 js 实现 vue 的某些功能
1.数据双向绑定:https://www.cnblogs.com/yuqing-o605/p/6790709.html?utm_source=itdadao&utm_medium=referr ...
- [CSP-S模拟测试]:w(树上DP)
题目背景 $\frac{1}{4}$遇到了一道水题,双完全不会做,于是去请教小$D$.小$D$看了${0.607}^2$眼就切掉了这题,嘲讽了$\frac{1}{4}$一番就离开了.于是,$\frac ...
- JS 替换
JS 字符串有replace() 方法.但这个方法只会对匹配到的第一个字串替换. 如下例: var str = "wordwordwordword"; var strNew = s ...
- idea中以maven工程的方式运行tomcat源码
0. 准备环境 idea+jdk8+tomcat源码 1.下载tomcat源码: http://mirrors.tuna.tsinghua.edu.cn/apache/tomcat/tomcat-8/ ...
- 小程序中封装base64
function Base64() { // private property var _keyStr = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmn ...