LongAdder浅析
LongAdder浅析
LongAdder类是在java8中新加入的并发环境下高性能的计数器类成员。该类主要通过CAS的原理和分散竞争的思想,实现并发环境下的计数效率。
该类继承了内部抽象类Striped64(基础计数器和分散竞争),并间接实现Number接口(负责数值类型的转换)。
其核心思想还是Striped64,该类的解析见Striped64学习。
LongAdder类是在java8中新加入的并发环境下高性能的计数器类成员。该类主要通过CAS的原理和分散竞争的思想,实现并发环境下的计数效率。
该类继承了内部抽象类Striped64(基础计数器和分散竞争),并间接实现Number接口(负责数值类型的转换)。
其核心思想还是Striped64,该类的解析见Striped64学习。
很长一段时间,不知道Striped64这个类的存在,当然,还是由于对并发包不了解的缘故。在大概了解了一下之后,才知道,原来这是一个并发计数组件,这个类很有意思,在这里学习总结一下。
Striped64是在java8中新增的用于支持累加器的并发组件(和LongAdder、DoubleAdder一起增加的一个抽象内部类),它支持在并发环境下计数,其设计思想是避免线程激烈竞争时引起的开销和异常,通过分散竞争的方式(允许不超过CPU核心数个线程同时执行)实现最大效率。
在Striped64内部维护了3个重要操作变量,分别是:cells(Cell类型的数组)、base(基础计数器)、cellsBusy(Cell数组状态值)。Cell对象内部维护了一个计数值value,用来记录线程局部计数值。
在连接SSH时候,往往要输入一串的命令,包括用户名密码及端口,比如ssh userName@serverIP
,该命令为连接到serverIP
端口号为22
的远程主机,连接时需要输入密码进行认证。这种方式命令较长较难记,如果密码也很难记,那每次SSH都很麻烦。
通过密钥认证方式可以在避免输入密码的情况下连接到SSH远程主机,该方式通过ssh-copy-id
将本地公钥传输到SSH远程主机的authorized_keys
文件中,目的是在SSH客户端登录的时候,通过该公钥来验证客户端。
ssh-copy-id
的基本语法为ssh-copy-id [-i [identity_file]] [user@]machine [-p port]
,其中,-i
为指定公钥文件,-p
为指定端口。
示例:
ssh-copy-id -i ~/.ssh/id_rsa.pub userName@serverIP -p port
如果用户权限不足,可以通过命令chmod 700 ~/.ssh
和chmod 600 ~/.ssh/authorized_keys
更改文件权限。
以上只是简化了密码的输入,还可以通过简化命令的方式实现快速进入,即通过配置命令别名的方式实现。在本地环境中,进入~/.bash_profile
文件,追加别名命令alais sshCommand="ssh userName@serverIP -p port"
,如果~/.bash_profile
文件不存在,则新建,配置完成后,通过命令source ~/.bash_profile
使其生效。
如果Mac中使用iterm
,可能快捷命令并不会生效,需要编辑.zshrc
文件,添加以下内容即可避免每次进入都需要使用source
命令编译。
1 | if [ -f ~/.bash_profile ]; then |
最后,在终端中输入命令别名sshCommand
即可连接到远程主机。
在Idea
中使用gradle5
配置springboot2
项目,该项目下有两个子项目,如:Project {subA, subB}
,其中subA
项目依赖subB(非springboot项目)
项目implementation project(':subB')
,在使用gradle build
时,控制台抛出类似如下异常:
1 | /Users/xxxx/xxx/xxx/solby/xboot/src/main/java/me/solby/xboot/tookit/aspect/RequestLimitAspect.java:6: 错误: 程序包me.solby.xoauth.common不存在 |
该类异常表示找不到类所在包,但是通过idea
的方式编译或运行,都不会有问题。
在SpringBoot多模块项目开发中,新增了国际化配置
1 | spring: |
Resource
目录下存在i18n/messages
,文件中配置key=value
。
使用时遇到org.springframework.context.NoSuchMessageException: No message found under code 'error.xxxx.message' for locale 'zh_CN_#Hans'
。
Resource
目录下文件是否存在;key=value
是否存在;经过排查,发现以上问题均不存在,且断点进入MessageSource
相关方法中发现parentMessageSource
始终为空。
后来,看了下messages
的配置位置,是在被依赖模块的application.yml
配置文件中,想到应该是项目启动后,使用过程中并未在启动项目的Resource
目录下发现i18n/messages
,而配置生效的路径则为被依赖模块的Resource
目录下,因此,导致在被依赖模块目录下找不到i18n/messages
而报错。
将配置转移到启动项目的配置文件中,再次测试国际化正常。
造成系统瓶颈计算资源的因素有很多,包括CPU资源的调度、内存的读写、磁盘IO、网络IO、数据库、竞争锁、异常等。而系统性能的衡量指标有响应时间、启动时间、执行时间、执行速度、磁盘吞吐量、网络吞吐量、负载承受能力等。那么,从软件的角度看,性能优化的目标有,编写更高效的代码、使用更高效的算法、减少竞争锁、分布式集群、微服务等。而性能的优化策略有,用空间换时间、用时间换空间、优化代码、并行处理等。系统的优化来自三个方面,基础技术、层次方面、架构方面。