高tps下,java性能调优

之前参与了系统调优,感觉挺有收获了,现在记录一下。

处理xml时,理清楚报文格式,避免使用jdom解析

我们在做压测的时候,发现有一个程序响应非常慢,使用jstack定位到慢的地方:解析xml报文。xml报文存储的是数据信息,存储的格式很简单。但是为啥这里会出现问题?我想可能是tps高的情况下,使用jdom解析xml时,会将整个xml报文整理成对象,这个操作即耗cpu又耗内存。我们就尝试使用最简单的字符串截取的方法,实现xml解析,tps果然提高了很多。

收获

在不同系统间做交互时,如果传递的信息比较简单,建议使用格式化的字符串,避免使用xml,json。

避免使用正则

我们在做一个功能的时候需要将一个以\t分隔的字符串的第某一位取出来。实现方法是:使用Stirng的split方法,将字符串转成数组,然后根据下标位置取出需要的数据。因为split底层还是使用的正则做的字符串分隔,这是非常消耗cpu的。我们尝试使用字符串截取的方式,实现了这个功能,tps得到了很大的提升。

收获

让你舒服的方法肯定不是性能最好的。

避免new对象,尽量可以控制创建对象的数量

我们格式化日期是经常使用simpledateformat对象,当时写的方法是每一次调用格式化日期都会new一个对象,高tps的情况下,new的对象多,多次gc,对影响程序的响应速度。我们尝试修改成单例,即每种日期模式只对应new一个对象,程序tps也得到了一定的提升。

收获

控制程序中实例化对象的数量。

错误的释放内存导致内存泄露

我们在压测的时候,出现的情况很奇怪,刚开始一切正常,但是逐渐程序变慢,到最后直接卡死,不响应请求。我们看了gc日志,发现程序不断的在gc。我们猜测应该是内存被撑爆了。顺着这个思想,找到释放缓冲这块代码,怀疑没有成功释放缓存。缓存是存储在map里,释放缓存是通过new的方式来实现了,这样是不能够释放缓存的。map中还有一个方法是clear(),这个方法可以释放内存吗?看一下源码:

public void clear() {
    modCount++;
    Entry[] tab = table;
    for (int i = 0; i < tab.length; i++)
        tab[i] = null;
    size = 0;
}

调用clear 方法后没有将entry清除掉,只是将每一个entry置空。这样hashmap的大小是不变的。

那么应该怎么将map的清空呢,最简单的方法就是清除所有对map里面entry的的引用即可。

参考代码

private static void releaseMap(Map map) {
	if (map==null) {
		return;
	}
	if (map.entrySet()==null) {
		return;
	}
	Iterator  iterator=map.entrySet().iterator();
	if (iterator==null) {
		return;
	}
	while(iterator.hasNext()){
		Object key=iterator.next();
		iterator.remove();
	}
}

收获

一个优秀的开发者总是会很好的控制自己使用的内存。

转载于:https://my.oschina.net/huaxiaoqiang/blog/1836328

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值