一 . split
除非是必须的,否则应该避免使用split,split由于支持正则表达式,所以效率比较低,如果是频繁的几十,几百万的调用将会耗费大量资源,如果确实需要频繁的调用split,可以考虑使用apache的StringUtils.split(string,char),频繁split的可以缓存结果。
二. +,stringbuilder,stringBuffer
A. +, 一般情况下性能差,但是 某些特别情况下, String 对象的字符串拼接其实是被 JVM 解释成了 StringBuffer 对象的拼接,所以这些时候 String 对象的速度并不会比 StringBuffer 对象慢,而特别是以下的字符串对象生成中, String 效率是远要比 StringBuffer 快的:
String S1 = “This is only a” + “ simple” + “ test”;
如果你的字符串是来自另外的 String 对象的话,速度就没那么快了,譬如:
String S2 = “This is only a”;
String S3 = “ simple”;
String S4 = “ test”;
String S1 = S2 +S3 + S4;
这时候 JVM 会规规矩矩的按照原来的方式去做
B, 大部分情况下 StringBuilder > StringBuffer>>+
StringBuilder 不保证同步
StringBuffer 线程安全(其中方法大量使用synchronized)
三. 缓存读取瓶颈
Redis,memcached不能无限读写的,连接数有限制。
官网测试结果
SET:198412.69/s
GET:198019.80/s
但是实际要考虑网络开销 等,实际远远达不到这个效果,再说一个redis未必就一个应用在用。
每次读取耗时虽少,累计就可观了,在循环中使用需谨慎
四 乘除操作
尽量使用移位来代替 a/b,a*b 操作,/是一个代码很高的操作
Int num=a>>2;
五 容器初始大小
Map等容器每次扩容,实际是新创建一个容器,然后拷贝。
预先设置合理的size, 避免扩容,节省很多资源开销
六 TreadLocal
ThreadLocal为每个使用该变量的线程提供独立的变量副本,所以每一个线程都可以独立地改变自己的副本,而不会影响其它线程所对应的副本。
看起来是没什么问题的,但是结合线程池使用就容易出问题了。
线程池的目的是重用线程,但是 ThreadLocal是上次使用时候存的值,切记切记,建议每次清空