实现Java线程安全
来源:互联网 发布:淘宝简易摄影棚 编辑:程序博客网 时间:2024/06/04 20:20
一个类如果想要满足线程安全的条件:
- 每个线程都能正常的执行原子操作,保证得到正确的结果
- 这个类的对象可以同时被多个线程安全的访问
- 在每个线程的原子操作都完成后,对象处于合理的状态
一般情况下不可变类总是线程安全的,因为他的对象的状态始终不会改变,任何线程只能读取他的状态,而不能改变他的状态,例如String类就是一个不可变类,因为String类在我们的代码中使用的实在是太多了,如果设计成可变类后果可想而知……对于那些可变类,如果想要保证它的们的线程安全,就要保证对于他们的原子操作进行同步。
我们常说StirngBuffer是线程安全的,StringBuilder是线程不安全的,为什么呢?因为在StringBuffer类中大量使用了同步,以下只是一小部分方法,方法都用synchronized关键字修饰,做到同步
但是大量运用同步可能对性能造成影响,同步的意思好比大家一起排队做某件事,举个例子i,有十个人去吃饭,但是饭店的座位只有一个,只能一个一个吃,第一个人先吃,这样依次下去,那么第十个人要等到前面九个人都吃完了才能吃饭,想想是不是很委屈。对可变类实现同步往往都会降低并发性能,为了减少带来的影响,我们可以采取下面的措施:
- 只对额能导致资源竞争的代码进行同步处理,对于那些没有资源竞争的代码不进行处理,例如我们在对一个属性提供set和get方法的时候,试着只提供get方法获取值,不提供set方法修改值,这样虽然好多个线程同时访问,也不会造成数据的错误和资源的竞争。
- 对于多线程环境下我们提供一个运行方式,对于单线程环境下提供一个运行方式。一个类提供两种实现方式,在单线程运行环境下采用微进行同步实现的代码,对于对线程运行环境下采用进行同步处理的代码,避免一刀切。这里有个很好的例子,Map,Set,List这三个集合类都是线程不安全的,在多线程环境下怎么办呢?Collections类提供了很好的解决办法,他提供了返回这些集合同步版本的静态内部类,并在类中重写了集合中所有有资源竞争的方法,加了synchronized关键字进行同步处理
SynchronizedCollection和三个集合一样,也是实现了同步的方法,看代码:
public static <T> List<T> synchronizedList(List<T> list) { return (list instanceof RandomAccess ? new SynchronizedRandomAccessList<>(list) : new SynchronizedList<>(list));}static <T> List<T> synchronizedList(List<T> list, Object mutex) { return (list instanceof RandomAccess ? new SynchronizedRandomAccessList<>(list, mutex) : new SynchronizedList<>(list, mutex));}/** * @serial include */static class SynchronizedList<E> extends SynchronizedCollection<E> implements List<E> { private static final long serialVersionUID = -7754090372962971524L; final List<E> list; SynchronizedList(List<E> list) { super(list); this.list = list; } SynchronizedList(List<E> list, Object mutex) { super(list, mutex); this.list = list; } public boolean equals(Object o) { if (this == o) return true; synchronized (mutex) {return list.equals(o);} } public int hashCode() { synchronized (mutex) {return list.hashCode();} } public E get(int index) { synchronized (mutex) {return list.get(index);} } public E set(int index, E element) { synchronized (mutex) {return list.set(index, element);} } public void add(int index, E element) { synchronized (mutex) {list.add(index, element);} } public E remove(int index) { synchronized (mutex) {return list.remove(index);} } public int indexOf(Object o) { synchronized (mutex) {return list.indexOf(o);} } public int lastIndexOf(Object o) { synchronized (mutex) {return list.lastIndexOf(o);} } public boolean addAll(int index, Collection<? extends E> c) { synchronized (mutex) {return list.addAll(index, c);} } public ListIterator<E> listIterator() { return list.listIterator(); // Must be manually synched by user } public ListIterator<E> listIterator(int index) { return list.listIterator(index); // Must be manually synched by user } public List<E> subList(int fromIndex, int toIndex) { synchronized (mutex) { return new SynchronizedList<>(list.subList(fromIndex, toIndex), mutex); } }
public static <T> Set<T> synchronizedSet(Set<T> s) { return new SynchronizedSet<>(s);}static <T> Set<T> synchronizedSet(Set<T> s, Object mutex) { return new SynchronizedSet<>(s, mutex);}/** * @serial include */static class SynchronizedSet<E> extends SynchronizedCollection<E> implements Set<E> { private static final long serialVersionUID = 487447009682186044L; SynchronizedSet(Set<E> s) { super(s); } SynchronizedSet(Set<E> s, Object mutex) { super(s, mutex); } public boolean equals(Object o) { if (this == o) return true; synchronized (mutex) {return c.equals(o);} } public int hashCode() { synchronized (mutex) {return c.hashCode();} }}
我们可以通过代码看到他是实现了一个静态方法,在静态方法中去创建这个静态类,而这个静态类重写了集合中有资源竞争关系的方法(加了同步处理)
参考:Java面向对象编程--孙卫琴
阅读全文
0 0
- JAVA实现线程安全
- 实现Java线程安全
- java实现线程安全的单利模式
- java中线程安全的实现方法
- Java多线程线程安全实现方式
- java 线程安全的实现方式
- Java线程安全的实现方法
- java实现线程安全的队列
- Java中的线程安全与实现
- java如何实现线程的安全:线程的同步机制
- Vector实现线程安全
- 线程安全实现方案
- 如何实现线程安全?
- 拿来主义:java中的线程安全与非线程安全,以及如何使用和实现
- Java线程安全和非线程安全
- Java线程安全和非线程安全
- Java线程安全和非线程安全
- Java线程安全和非线程安全
- Qt 学习之路 2(17):文件对话框
- git提示error setting certificate verify locations解决办法
- pygame 文字保存成png格式透明背景
- Ubuntu
- (四)面向对象编程
- 实现Java线程安全
- python_numpy的矩阵运算及对应的matlab写法
- JVM—HotSpot虚拟机探秘
- 自定义Volley
- Python入门4:文件访问与函数式编程入门
- Perlin Noise变种及无缝纹理生成
- postman发送get\post请求
- Qt+opencv二值化
- git 的最基本操作