论坛首页 Java企业应用论坛

关于性能优化

浏览 39921 次
精华帖 (2) :: 良好帖 (10) :: 新手帖 (0) :: 隐藏帖 (1)
作者 正文
   发表时间:2010-11-16  
ironsabre 写道
flysnowxf 写道
汗,这是很基础的概念了。
百度百科:http://baike.baidu.com/view/714962.htm

引用
当以前分配的一片内存不再需要使用或无法访问时,但是却并没有释放它,那么对于该进程来说,会因此导致总可用内存的减少,这时就出现了内存泄漏。


再说一次,向集合里一直加东西不删除,这个不叫内存泄漏。


那是你的理解了。我的理解是,分配了内存,但这些内存不再被使用,比如过期了、没用了,但又没有去删除,造成内存占用越来越多。HashMap的使用就容易出现这个问题。
0 请登录后投票
   发表时间:2010-11-16  
flysnowxf 写道
ironsabre 写道
flysnowxf 写道
汗,这是很基础的概念了。
百度百科:http://baike.baidu.com/view/714962.htm

引用
当以前分配的一片内存不再需要使用或无法访问时,但是却并没有释放它,那么对于该进程来说,会因此导致总可用内存的减少,这时就出现了内存泄漏。


再说一次,向集合里一直加东西不删除,这个不叫内存泄漏。


那是你的理解了。我的理解是,分配了内存,但这些内存不再被使用,比如过期了、没用了,但又没有去删除,造成内存占用越来越多。HashMap的使用就容易出现这个问题。


哎。你这个没过期,也有用。你可以通过HashMap取出来值的,这怎么能叫泄漏呢?
我现在总是你,如果你向cache里放了100个对象,永远keep住,如果我应用程序经常来访问它,叫不叫泄漏?
如果我应用程序再也不来访问它,叫不叫泄漏?
按你的理解,第一种不叫,第二种叫。可这两种没有区别。我不可能用由第三方来判断我自己是不是泄漏,明白吗?

下面这个Stack,在被别人用的时候,可能会引起泄漏。你先找找看哪行会出总是。然后再理解一下跟你这个有什么区别。
import java.util.Arrays;
import java.util.EmptyStackException;

public class Stack {
private Object[] elements;
private int size = 0;
private static final int DEFAULT_INITIAL_CAPACITY = 16;

public Stack() {
elements = new Object[DEFAULT_INITIAL_CAPACITY];
}

public void push(Object e) {
ensureCapacity();
elements[size++] = e;
}

public Object pop() {
if (size == 0)
throw new EmptyStackException();
return elements[--size];
}

/**
* Ensure space for at least one more element, roughly doubling the capacity
* each time the array needs to grow.
*/
private void ensureCapacity() {
if (elements.length == size)
elements = Arrays.copyOf(elements, 2 * size + 1);
}
}
0 请登录后投票
   发表时间:2010-11-16  
Java程序确实也有很多需要优化的地方,但更重要的是庞大的数据库存取优化
0 请登录后投票
   发表时间:2010-11-16  
性能是什么指标? 就是你使用中发现达不到自己的要求标准(或者是预计到某段时间后达不到期望底限了)了,这样的情况下才想到优化,而优化往往和重构一起出现,学会分析优化才是最关键的,不要以为每一句代码都对性能起到关键性的影响,分析性能瓶颈,提出可行方案,验证优化结果,不行就继续调整方案。这才是优化的思想。不要为了优化而优化,没有可预计的用途不要为了重构而去重构,即使代码你觉得很乱。
0 请登录后投票
   发表时间:2010-11-16  
piao_bo_yi 写道
我发现一个现象,很多两三年以下的人写代码动不动就扯性能,其实他们大部分人根本不知道到底哪是性能瓶颈,函数调用的效率,CPU执行指令需要的时间...工作效率低不说,还考虑很多没用的东西。个人感觉,性能这个东西应该考虑:
1.考虑程序的应用范围。如果你是给核反应堆写实时程序,那每一步你可能都得考虑,其他就大部分通用程序而言,你不用每一步都考虑。
2.性能要考虑关键瓶颈。不是每一步都是关键,关键瓶颈不是写之前提前考虑出来的,而是测出来的。很多你以为瓶颈的地方往往不是瓶颈。
3.低效的算法+大量的处理数据两者结合往往是导致效率低下的根本原因,而函数调用,拆分函数等不是。JAVA初学者喜欢怀疑函数调用,C++派则彻底怀疑继承结构和堆上的数据,很有意思的现象。即使低效的算法处理小量数据也没必要优化,e.g.冒泡排序和快速排序在排少量数据的时候的性能差异不需要考虑。

大家说说自己的看法。

P.S.编程里面真的有很多不符合直觉的结论。比如边开发边考虑性能优化是否必要,比如添加人手是否能提高项目进度,真的是很有意思。


赞同楼主的看法。
如果再加上根据开发规范(这个规范并没有统一的),进行代码书写就更加完美了:)
0 请登录后投票
   发表时间:2010-11-16  
jdk 6后系统性能已经好了很多,扣个几行代码或者函数调用少几次效果不明显

性能问题最大的还是I/O操作,比如文件I/O,网络I/O(数据库,rpc调用)等,像数据库少调用一次平均可以减少2ms,这可以执行几亿次for循环了

0 请登录后投票
   发表时间:2010-11-16  
ironsabre 写道
flysnowxf 写道
ironsabre 写道
flysnowxf 写道
汗,这是很基础的概念了。
百度百科:http://baike.baidu.com/view/714962.htm

引用
当以前分配的一片内存不再需要使用或无法访问时,但是却并没有释放它,那么对于该进程来说,会因此导致总可用内存的减少,这时就出现了内存泄漏。


再说一次,向集合里一直加东西不删除,这个不叫内存泄漏。


那是你的理解了。我的理解是,分配了内存,但这些内存不再被使用,比如过期了、没用了,但又没有去删除,造成内存占用越来越多。HashMap的使用就容易出现这个问题。


哎。你这个没过期,也有用。你可以通过HashMap取出来值的,这怎么能叫泄漏呢?
我现在总是你,如果你向cache里放了100个对象,永远keep住,如果我应用程序经常来访问它,叫不叫泄漏?
如果我应用程序再也不来访问它,叫不叫泄漏?
按你的理解,第一种不叫,第二种叫。可这两种没有区别。我不可能用由第三方来判断我自己是不是泄漏,明白吗?

下面这个Stack,在被别人用的时候,可能会引起泄漏。你先找找看哪行会出总是。然后再理解一下跟你这个有什么区别。
import java.util.Arrays;
import java.util.EmptyStackException;

public class Stack {
private Object[] elements;
private int size = 0;
private static final int DEFAULT_INITIAL_CAPACITY = 16;

public Stack() {
elements = new Object[DEFAULT_INITIAL_CAPACITY];
}

public void push(Object e) {
ensureCapacity();
elements[size++] = e;
}

public Object pop() {
if (size == 0)
throw new EmptyStackException();
return elements[--size];
}

/**
* Ensure space for at least one more element, roughly doubling the capacity
* each time the array needs to grow.
*/
private void ensureCapacity() {
if (elements.length == size)
elements = Arrays.copyOf(elements, 2 * size + 1);
}
}


为什么类似问题总是直接照抄effective java的示例代码?


0 请登录后投票
   发表时间:2010-11-16  
flysnowxf 写道
ironsabre 写道
qianhd 写道
对于新手 写的时候动动脑子 别写出内存泄漏的代码 就谢天谢地了

有些人习惯性的爱写内存泄漏的代码
真不知道怎么想的


我觉得新手想要写出内存泄漏的代码是很难的,或者说你让他写一段内存泄漏的代码他都写不出来。要不你写一个试试?

如果写本地缓存的话,是很容易出现的。比如new HashMap(),然后不断往里边put(Object),但却不记得remove或者后台起一个线程去remove,结果hashMap里边的数据越来越多,里边引用的Object却不能被垃圾收回。这种内存泄露的情况非常普遍。

关于性能优化,在没有经验积累的情况,建议先测出来瓶颈在哪里。比如jprofile就很容易分析出哪段代码花费cpu的时间比较长。以我的经验来看,性能瓶颈主要在数据库和网络通信。


见过for里面有数据库操作的飘过。
0 请登录后投票
   发表时间:2010-11-16  
你是给客户做东西,你问了客户是否满意吗?
别老犯程序员老毛病“自以为是”
到处折腾所谓的“性能”
0 请登录后投票
   发表时间:2010-11-16  
ironsabre 写道
flysnowxf 写道
ironsabre 写道
flysnowxf 写道
汗,这是很基础的概念了。
百度百科:http://baike.baidu.com/view/714962.htm

引用
当以前分配的一片内存不再需要使用或无法访问时,但是却并没有释放它,那么对于该进程来说,会因此导致总可用内存的减少,这时就出现了内存泄漏。


再说一次,向集合里一直加东西不删除,这个不叫内存泄漏。


那是你的理解了。我的理解是,分配了内存,但这些内存不再被使用,比如过期了、没用了,但又没有去删除,造成内存占用越来越多。HashMap的使用就容易出现这个问题。


哎。你这个没过期,也有用。你可以通过HashMap取出来值的,这怎么能叫泄漏呢?
我现在总是你,如果你向cache里放了100个对象,永远keep住,如果我应用程序经常来访问它,叫不叫泄漏?
如果我应用程序再也不来访问它,叫不叫泄漏?
按你的理解,第一种不叫,第二种叫。可这两种没有区别。我不可能用由第三方来判断我自己是不是泄漏,明白吗?

下面这个Stack,在被别人用的时候,可能会引起泄漏。你先找找看哪行会出总是。然后再理解一下跟你这个有什么区别。
import java.util.Arrays;
import java.util.EmptyStackException;

public class Stack {
private Object[] elements;
private int size = 0;
private static final int DEFAULT_INITIAL_CAPACITY = 16;

public Stack() {
elements = new Object[DEFAULT_INITIAL_CAPACITY];
}

public void push(Object e) {
ensureCapacity();
elements[size++] = e;
}

public Object pop() {
if (size == 0)
throw new EmptyStackException();
return elements[--size];
}

/**
* Ensure space for at least one more element, roughly doubling the capacity
* each time the array needs to grow.
*/
private void ensureCapacity() {
if (elements.length == size)
elements = Arrays.copyOf(elements, 2 * size + 1);
}
}


既然那些对象我一直在用,那为什么会被叫做是泄露?难道我用那100个对象也有错?
应该是当我没用那所有对象,或者是某些对象的时候,又没有在Map里面remove掉那些对象,导致了map一直持有引用,根据gc的原理,这样的对象是不会被回收的,这样才造成了泄露吧.这是我的理解
0 请登录后投票
论坛首页 Java企业应用版

跳转论坛:
Global site tag (gtag.js) - Google Analytics