集合类不安全(Juc-03)

野生程序员 Life is fucking movie ,we all performer !We all no more younger! 本文由博客端 http://localhost 主动推送

List

list 不安全在哪里,如何解决,各种解决方案的好处

package net.yscxy.unsafe;

import java.util.*;
import java.util.concurrent.CopyOnWriteArrayList;

/**
 * @Author WangFuKun
 * @create 2020/11/21 9:01
 */
//java.util.ConcurrentModificationException 并发修改异常
/*
 *所有集合的老大Collections
 * 解决方案
 * 1.用Vector解决  List<String> list = new Vector<>();
 * 2. List<String> list =Collections.synchronizedList(new ArrayList<>());
 * 3.写入时复制 多个线程调用的时候读取的时候是固定的,写入的时候(覆盖)
 * 在写入的时候避免覆盖,造成数据问题
 *  List<String> list = new CopyOnWriteArrayList<>();
 * 4.对比 CopyOnWriteArrayList 比 Vector好在哪里
 * 因为Vector用的是synchronized 但是CopyOnWriteArrayList用的是lock,synchronized效率比较低
 * */
public class ListTest {
    public static void main(String[] args) {
//       List<String> list = new ArrayList<>();
//        List<String> list = new Vector<>();

        List<String> list = new CopyOnWriteArrayList<>();
        for (int i = 0; i < 100; i++) {
            new Thread(() -> {
                list.add(UUID.randomUUID().toString().substring(0, 5));
                System.out.println(list);
            }, String.valueOf(i)).start();
        }
    }
}

Set

package net.yscxy.unsafe;

import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
import java.util.UUID;
import java.util.concurrent.CopyOnWriteArraySet;

/**
 * @Author WangFuKun
 * @create 2020/11/21 9:27
 */
/*
 * java.util.ConcurrentModificationException
 * 解决方案
 *1. Set<String> set = Collections.synchronizedSet(new HashSet<>());(工具类写法)
 *2. Set<String> set = new CopyOnWriteArraySet<>();(juc写方法)
 * */

public class SetTest {
    public static void main(String[] args) {
        //  Set<String> set = new HashSet<>();
        //Set<String> set = Collections.synchronizedSet(new HashSet<>());
        Set<String> set = new CopyOnWriteArraySet<>();
        for (int i = 0; i < 30; i++) {
            new Thread(() -> {
                set.add(UUID.randomUUID().toString().substring(0, 5));
                System.out.println(set);
            }, String.valueOf(i)).start();
        }
    }
}

那么 HashSet 的底层是什么呢?

public HashSet() {
        map = new HashMap<>();
    }

//add方法本质就是map的key
public boolean add(E e) {
        return map.put(e, PRESENT)==null;
    }
//PRESENT 不变的值
private static final Object PRESENT = new Object();

Map

回顾 map 的基本操作

image.png

package net.yscxy.unsafe;

import java.util.*;
import java.util.concurrent.ConcurrentHashMap;

/**
 * @Author WangFuKun
 * @create 2020/11/21 9:46
 */
/*
 * java.util.ConcurrentModificationException 并发修改异常
 * 解决方案:
 * 1.Map<String, Object> map = Collections.synchronizedMap(new HashMap<>());(工具类)
 * 2. new ConcurrentHashMap<>();(juc下的)
 * */
public class MapTest {
    public static void main(String[] args) {
        //面试题1.map是这样用的吗? 不是,工作中不用这个
        // 2.默认等价于什么? 默认等价于new HashMap<>(16,0.75);加载因子,初始化容量
        //Map<String, Object> map = new HashMap<>();
        // Map<String, Object> map = Collections.synchronizedMap(new HashMap<>());
        Map<String, Object> map = new ConcurrentHashMap<>();
        for (int i = 0; i < 1000; i++) {
            new Thread(() -> {
                map.put(Thread.currentThread().getName(), UUID.randomUUID().toString().substring(0, 5));
                System.out.println(map);
            }, String.valueOf(i)).start();
        }
    }
}
  • juc
    10 引用 • 2 回帖

赞助商 我要投放

欢迎来到这里!

我们正在构建一个小众社区,大家在这里相互信任,以平等 • 自由 • 奔放的价值观进行分享交流。最终,希望大家能够找到与自己志同道合的伙伴,共同成长。

注册 关于
请输入回帖内容 ...