线程封闭
把对象封装到一个线程中,只有一个线程能看到这个对象。
import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.boot.web.servlet.FilterRegistrationBean; import org.springframework.context.annotation.Bean; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter; @SpringBootApplication public class ConcurrencyApplication extends WebMvcConfigurerAdapter { public static void main(String[] args) { SpringApplication.run(ConcurrencyApplication.class,args); } @Bean public FilterRegistrationBean httpFilter(){ FilterRegistrationBean registrationBean=new FilterRegistrationBean(); registrationBean.setFilter(new HttpFilter()); registrationBean.addUrlPatterns("/threadLocal/*"); return registrationBean; } @Override public void addInterceptors(InterceptorRegistry registry) { registry.addInterceptor(new HttpInterceptor()).addPathPatterns("/**"); } }
public class RequestHolder { private final static ThreadLocal<Long> requestHolder=new ThreadLocal<>(); public static void add(Long id){ requestHolder.set(id); } public static Long getId(){ return requestHolder.get(); } public static void remove(){ requestHolder.remove(); }
import com.example.threadLocal.RequestHolder; import lombok.extern.slf4j.Slf4j; import javax.servlet.*; import javax.servlet.http.HttpServletRequest; import java.io.IOException; @Slf4j public class HttpFilter implements Filter { @Override public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException { HttpServletRequest request=(HttpServletRequest) servletRequest; log.info("do filter,{},{}",Thread.currentThread().getId(),request.getServletPath()); RequestHolder.add(Thread.currentThread().getId()); filterChain.doFilter(servletRequest,servletResponse); } @Override public void init(FilterConfig filterConfig) throws ServletException{ } @Override public void destroy() { } }
import com.example.threadLocal.RequestHolder; import lombok.extern.slf4j.Slf4j; import org.springframework.web.servlet.handler.HandlerInterceptorAdapter; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; @Slf4j public class HttpInterceptor extends HandlerInterceptorAdapter { @Override public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { log.info("preHandle"); return true; } @Override public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception { RequestHolder.remove(); log.info("afterCompletion"); return; } }
import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.boot.web.servlet.FilterRegistrationBean; import org.springframework.context.annotation.Bean; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter; @SpringBootApplication public class ConcurrencyApplication extends WebMvcConfigurerAdapter { public static void main(String[] args) { SpringApplication.run(ConcurrencyApplication.class,args); } @Bean public FilterRegistrationBean httpFilter(){ FilterRegistrationBean registrationBean=new FilterRegistrationBean(); registrationBean.setFilter(new HttpFilter()); registrationBean.addUrlPatterns("/threadLocal/*"); return registrationBean; } @Override public void addInterceptors(InterceptorRegistry registry) { registry.addInterceptor(new HttpInterceptor()).addPathPatterns("/**"); } }
import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Semaphore; public class StringExample2 { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static StringBuffer stringBuffer=new StringBuffer(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ executorService.execute(()->{ try { semaphore.acquire(); update(); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",stringBuffer.length()); } private static void update(){ stringBuffer.append("1"); } }
public class StringExample1 { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static StringBuilder stringBuilder=new StringBuilder(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ executorService.execute(()->{ try { semaphore.acquire(); update(); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",stringBuilder.length()); } private static void update(){ stringBuilder.append("1"); } }
import java.util.HashSet; import java.util.Set; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Semaphore; @Slf4j @NotThreadSafe //线程不安全 public class HashSetExample { public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static Set<Integer> set=new HashSet<>(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",set.size()); } private static void update(int i){ set.add(i); } }
import com.example.annoations.NotThreadSafe; import lombok.extern.slf4j.Slf4j; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Semaphore; import java.util.ArrayList; import java.util.List; @Slf4j @NotThreadSafe //执行的结果并不是5000,线程不安全 public class ArrayListExample { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static List<Integer> list=new ArrayList<>(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",list.size()); } private static void update(int i){ list.add(i); } }
import java.util.HashMap; import java.util.Map; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Semaphore; @Slf4j @NotThreadSafe public class HashMapExample { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static Map<Integer,Integer> map=new HashMap<>(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",map.size()); } private static void update(int i){ map.put(i,i); } }
import java.util.Vector; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Semaphore; @Slf4j @ThreadSafe public class VectorExample1 { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static Vector<Integer> list=new Vector<>(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",list.size()); } private static void update(int i){ list.add(i); } }
import java.util.Vector; @NotThreadSafe public class VectorExample2 { private static Vector<Integer> vector=new Vector<>(); public static void main(String[] args) { while (true) { for (int i = 0; i < 10; i++) { vector.add(i); } Thread thread = new Thread() { public void run() { for (int i = 0; i < 10; i++) { vector.remove(i); } } }; Thread thread2 = new Thread() { public void run() { for (int i = 0; i < 10; i++) { vector.get(i); } } }; thread.start(); thread2.start(); } } }
import java.util.Hashtable; import java.util.Map; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Semaphore; @Slf4j
//线程安全 public class HashTableExample { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static Map<Integer,Integer> map=new Hashtable<>(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",map.size()); } private static void update(int i){ map.put(i,i); } }
import com.example.annoations.ThreadSafe; import com.google.common.collect.Lists; import lombok.extern.slf4j.Slf4j; import java.util.Collections; import java.util.List; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Semaphore; @Slf4j @ThreadSafe public class CollectionsExample { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static List<Integer> list= Collections.synchronizedList(Lists.newArrayList()); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",list.size()); } private static void update(int i){ list.add(i); } }
import com.example.annoations.ThreadSafe; import com.google.common.collect.Sets; import lombok.extern.slf4j.Slf4j; import java.util.Collections; import java.util.Set; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Semaphore; @Slf4j @ThreadSafe public class CollectionsSetExample { public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static Set<Integer> set= Collections.synchronizedSet(Sets.newHashSet()); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",set.size()); } private static void update(int i){ set.add(i); } }
import com.example.annoations.ThreadSafe; import lombok.extern.slf4j.Slf4j; import java.util.Collections; import java.util.HashMap; import java.util.Map; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Semaphore; @Slf4j @ThreadSafe public class CollectionsHashMapExample { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static Map<Integer,Integer> map= Collections.synchronizedMap(new HashMap<>()); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",map.size()); } private static void update(int i){ map.put(i,i); } }
import java.util.Iterator; import java.util.Vector; public class VectorExample3 { //java.util.ConcurrentModificationException private static void test1(Vector<Integer> v1){ for(Integer i:v1){ if(i.equals(3)){ v1.remove(i); } } } //java.util.ConcurrentModificationException private static void test2(Vector<Integer> v1){ Iterator<Integer> iterator=v1.iterator(); while (iterator.hasNext()){ Integer i=iterator.next(); if(i.equals(3)){ v1.remove(i); } } } //成功 private static void test3(Vector<Integer> v1){ for(int i=0;i<v1.size();i++){ if(v1.get(i).equals(3)){ v1.remove(i); } } } public static void main(String[] args) { Vector<Integer> vector=new Vector<>(); vector.add(1); vector.add(2); vector.add(3); test2(vector); } }
适用读多写少的场景
设计思想:读写分离,最终一致性,使用时另外开辟空间,读不需要加锁,写需要加锁
import lombok.extern.slf4j.Slf4j; import java.util.List; import java.util.concurrent.*; @Slf4j public class CopyOnWriteArrayListExample { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static List<Integer> list=new CopyOnWriteArrayList<>(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",list.size()); } private static void update(int i){ list.add(i); } }
import lombok.extern.slf4j.Slf4j; import java.util.Set; import java.util.concurrent.*; @Slf4j public class ConcurrentSkipListSetExample { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static Set<Integer> list=new ConcurrentSkipListSet<>(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",list.size()); } private static void update(int i){ list.add(i); } }
import lombok.extern.slf4j.Slf4j; import java.util.Set; import java.util.concurrent.*; @Slf4j public class CopyOnWriteArraySetExample { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static Set<Integer> list=new CopyOnWriteArraySet<>(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",list.size()); } private static void update(int i){ list.add(i); } }
concurrentHashMap不允许空值
ConcurrentSkipListMap的key是有序的
import com.example.annoations.ThreadSafe; import lombok.extern.slf4j.Slf4j; import java.util.Map; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Semaphore; @Slf4j @ThreadSafe public class ConcurrentHashMap { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static Map<Integer,Integer> map=new java.util.concurrent.ConcurrentHashMap<>(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",map.size()); } private static void update(int i){ map.put(i,i); } }
import com.example.annoations.ThreadSafe; import lombok.extern.slf4j.Slf4j; import java.util.Map; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Semaphore; @Slf4j @ThreadSafe public class ConcurrentSkipListMapExample { //请求总数 public static int clientTotal=5000; //同时并发执行的线程数 public static int threadTotal=200; public static Map<Integer,Integer> map=new java.util.concurrent.ConcurrentSkipListMap<>(); public static void main(String[] args) throws Exception{ ExecutorService executorService= Executors.newCachedThreadPool(); final Semaphore semaphore=new Semaphore(threadTotal); final CountDownLatch countDownLatch=new CountDownLatch(clientTotal); for(int i=0;i<clientTotal;i++){ final int count=i; executorService.execute(()->{ try { semaphore.acquire(); update(count); semaphore.release(); }catch (Exception e){ log.error("exception",e); } countDownLatch.countDown(); }); } countDownLatch.await(); executorService.shutdown(); log.info("size{}",map.size()); } private static void update(int i){ map.put(i,i); } }