Johnny Shieh

人如果没有梦想,跟咸鱼有什么分别


  • 首页

  • 分类

  • 归档

  • 标签

  • 读书

  • 小伙伴

  • 关于

  • 搜索

线程安全之 volatile 关键字

发表于 2017-02-25 | 分类于 Java | | 阅读次数

在阅读本文前,建议先看下面两篇文章:

Java 内存模型

线程安全之 synchronized 关键字

Java 中 volatile 是轻量级的 synchronized,不会引起线程上下文的切换和调度。虽然 volatile 关键字只能修饰变量,但是要用好它并不容易,下面分析它的原理及注意事项。

volatile 关键字的两层语义

  • 保证变量对所有线程的可见性,即一个线程修改了某个值,新值对其他线程来说是立即可见的

  • 禁止指令重排序(Java 5 后才有的)

阅读全文 »

[译]通过 Hardware Layer 提升 Android 动画性能

发表于 2017-01-11 | 分类于 Android | | 阅读次数

当有人问我关于动画性能表现不佳问题时,我首先会问他们是否使用 Hardware layer。

在动画过程中你的视图可能在每一帧都需要进行重绘。如果使用 Hardware layer,可以避免重绘每一帧,因为 View 的渲染一旦进入离屏缓冲区就能够被复用。

另外,Hardware Layer 缓存在 GPU 上,它能够使动画中的某些操作变得更顺畅。通过使用 Hardware Layer 能够迅速渲染简单的变换(如,移动,旋转,缩放,透明度)。因为许多动画都是多种变换的组合,所以使用 Hardware Layer 能够显著提高动画性能。

用法

在使用 Hardware layer 之前,你的视图需要启用硬件加速,可以在 AndroidManifest 文件中的 application 或所在的 activity 加上android:hardwareAccelerated="true", 当 Target API >= 14 时,硬件加速是默认启用的。

View 的 layer API 非常简单:View.setLayerType()。你应该只是暂时设置 Hardware Layer,因为它们无法自动释放(稍后介绍)。基本使用步骤如下:

阅读全文 »

线程安全之 synchronized 关键字

发表于 2017-01-10 | 分类于 Java | | 阅读次数

一般在遇到线程安全的问题时候,大家都经常会使用 synchronized 关键字,来达到线程互斥访问的目的,但是这也间接造成它被程序员滥用的局面。下面分析 synchronized 关键字的原理、用法以及注意事项,帮助大家更好地使用它。

synchronized 的用法

synchronized 关键字可以修饰代码块或者方法,是最基本的互斥同步手段,可以避免多个线程之间的竞争条件(race conditions)。

1
2
3
4
5
// 修饰代码块
synchronized (ReferenceType) {...}
// 修饰方法(包括静态方法)
synchronized MethodDeclaration

实现原理

synchronized 关键字可以使得同一时刻只有一个线程能访问一个代码块或者方法,但是其内部原理究竟是如何呢。要理解其原理,首先要知道一点:所有对象都自动含有单一的锁与其对应(每个已加载的类对象也对应一个锁),这个锁也叫作互斥锁。用 synchronized 修饰即代表着加了某一个对象的锁,修饰代码块时明确指明是什么对象的锁,而在修饰方法时,如果修饰成员方法,指被调用该方法对象的锁,如果修饰静态方法,指该 Class 类型的锁。

在线程执行到 synchronized 修饰的代码块或者方法时,会尝试获取一个对象的互斥锁,执行完后会释放这个锁。如果获取对象锁失败,当前线程就要阻塞等待,所以当一个线程持有一个对象的锁时,其他线程无法获得这个锁,从而达到互斥访问的目的。在执行 synchronized 方法或 synchronized 代码块时出现异常,JVM 会自动释放获取的锁。

阅读全文 »

Java 内存模型

发表于 2017-01-05 | 分类于 Java | | 阅读次数

为了写出正确工作的并发程序,我们非常有必要理解 Java 内存模型。Java 内存模型描述了不同线程如何以及何时可以看到被其他线程修改后的共享变量的值,以及如何对共享变量执行同步操作。下面从一些基本概念开始解析 Java 内存模型,让大家理解多线程通信时需要注意的一些事项。

内存模型

由于计算机的内存与处理器的运算速度有几个数量级的差距,所以现代计算机系统都会加入一层或多层读写速度接近处理器运算速度的高速缓存作为中间缓冲:将运算需要的数据先复制到缓存中,让运算更快地进行,当运算结束后再从缓存同步会内存中,这样处理器就无须等待缓慢的内存读写。但是这样会引入缓存一致性问题,在多处理器系统中,每个处理器有独立的高速缓存,而它们又共享同一主内存,所以在修改同一内存区域时,不知道以哪个缓存数据为准。下图描述了处理器、高速缓存与主内存之间的交互关系:

在操作系统中,cpu 的最小执行单位是线程,所以在计算机系统中,内存模型是线程对内存或高速缓存读写过程的抽象。

阅读全文 »

2016 年终总结

发表于 2016-12-31 | 分类于 随笔 | | 阅读次数

不知不觉 2016 又要过去了,去年开始计划每年的最后一天写一篇年终总结,所以在元旦来临之前总结下今年的经历,迎接新一年的到来。

首先值得高兴的是,可以通过百度直接搜索到我的博客了,去年还是不能搜索到的。博客的样式也在闲余时间中修修改改,现在的样式自己比较满意。不过今年才写了 12 篇博客,上半年工作比较忙,工作中做的需求也没学到多少新鲜的知识,所以有几个月都没写博客。在新的一年要更好地管理时间,多自学新技术,提高博客输出产能。

上半年写了一个基于 Volley 扩展的网络请求框架 VolleyEx ,学习了网络请求和图片加载的相关内容,但后面看到了 Retrofit 的设计,架构非常优美,所以记录自己扩展 Volley 框架的文章就写了2篇就停止了。后面在几个月的空闲时间中写了干货集中营的移动 App,主要是为了学习 RxJava、Retrofit、Dagger2、Glide 等流行的开源框架,这个项目 – Gank 在 Github 上的 Star 数有两百多,是我目前的第一个开源项目,有这么多人赞同很开心。

阅读全文 »
1…8910…16
Johnny Shieh

Johnny Shieh

我本微末,心向天空

76 日志
13 分类
43 标签
GitHub Weibo Gmail 简书
  • 热门系列
  • Dagger 完全解析(6)
  • AspectJ in Android(3)
  • Kotlin 写 Android 单元测试(4)
  • Kotlin 协程完全解析(5)
© 2015 - 2019 Johnny Shieh
访客数 访问量