论坛首页 入门技术论坛

java线程死锁与内存溢出

浏览 36533 次
该帖已经被评为新手帖
作者 正文
   发表时间:2009-01-08  
使用ArrayList会内存溢出,被楼主雷到了。

使用Connection这个也被楼主雷到了。

开源框架倒在楼主的脚下。
0 请登录后投票
   发表时间:2009-01-08  
有些连接池中取出来的连接,在使用完后也是需要close的
这个close不是真正的close,而是将连接还给连接池
一般的连接池都是延迟一段时间(一般会有几分钟至几十分钟不等)才自动回收
这样也会造成连接池认为自己没有可用连接了,从而死锁
0 请登录后投票
   发表时间:2009-01-08  
public static DDConnectionBroker broker = null;

静态的,真不能随便用;尤其静态变量;
0 请登录后投票
   发表时间:2009-01-09   最后修改:2009-01-09
看了楼主的代码,感觉以楼主的水平,自己做个这个还是很冒险的。
看的有些晕,为什么要把Connection和Statement作为成员变量呢??Connection和Statement是那个broker来管理的吧?
你这样把它们做成成员变量,这个Data就是“有状态的”了,在多线程的情况下容易出问题。

我还是没明白为什么同时获取连接时会死锁,再看看。

这个:
#       try{  
#               
#             Conn = broker.getConnection();  
#             stmt=Conn.createStatement();  
#         }catch(Exception ex){  
#             ex.printStackTrace();  
#             //cf.close();  
#         }   

如果stmt=Conn.createStatement();  这一句抛出异常了,那上面的Conn是不是就没人管了?出异常后不释放掉么?

    还有你的那个加sychronized的办法,你确定是什么原因造成的么?
    在getConnection和connClose前面加上sychronized关键字,只会对同一个Data实例加上锁,对于多个Data实例没效果。不过看前面你说的Data是个单例的,那就不存在多个实例的情况了——但没见过单例这么写的,别人再用这个代码时,通过读你的代码,是怎么也想不到这个Data要求是单例的。

    Data只有一个实例,那相应的Conn也一直只有一份儿(至少是你能持有的只有一个)——这是我们用连接池的目的么??那把Conn也声明成static好了,反正全局只用一个。

把下面这个留言好好看看吧!
   
引用
repsihWDX

     我指的是你的Data类是不是单例。
如果是单例,那么虽然您的broker是不会重复的,但您每次都从新从broker里面拿连接,但又没传到外面用,赋予了您在单例的data中的那个Connection引用。
那么,如果原来Connection那个引用已经持有了一个连接实例,它在哪儿被关闭呢?
   



另外,
# se.printStackTrace();  
#                 System.out.println( se.getMessage() );  
#                 System.out.println( "Could not construct a broker, quitting." ); 

我现在再见到这种写法,属实感觉别扭。我们都用log来输出了。还什么printStackTrace(),System.out呢……
0 请登录后投票
   发表时间:2009-01-09  
System.out会占用大量IO,对性能是隐患.
lz自己写连接池,用来学习练手是好的,真正项目中绝对不要用,否则会死的很难看
就lz贴的代码问题太多,把dbcp的代码看看对照一下就知道了,连接池不是这么简单的.
0 请登录后投票
   发表时间:2009-01-11  
看一下common pool的源代码,肯定有所帮助。
0 请登录后投票
   发表时间:2009-01-12  
LZ,你太牛逼了
0 请登录后投票
   发表时间:2009-01-12  
你这个叫连接池?
你这个情况叫死锁?
其实根本就是线程不安全,导致很多连接没有正常关掉(连接的引用也丢失了,所以永远关不掉),接着再开连接就全部只能等待了。
死锁是不同同步块嵌套了才有可能产生的。你原来的代码一个同步都没有怎么可能死锁...
0 请登录后投票
   发表时间:2009-01-13  
谁最开始就写高质量的代码?

楼主,你的代码质量的确很成问题,大家都喷了,我就不喷了。。。。。

现在有两个修改办法:

1.这个比较累,建议你使用DBCP或者C3P0配合Hibernate或者IBatis重写你的程序。

2.将你connetion从成员变量中干掉,并使用synchronized同步你的方法和变量。。。这个是丑陋中的稍微不丑陋的一点方法。


算了,你还是按方法1来吧。。。。
0 请登录后投票
   发表时间:2009-01-13  
repsihWDX 写道
# try{ 
#              
#             Conn = broker.getConnection(); 
#             stmt=Conn.createStatement(); 
#         }catch(Exception ex){ 
#             ex.printStackTrace(); 
#             //cf.close(); 
#         }  

1.无finally,不关连接。try中的东西出异常你的这个connection费了。

2.如果这个类是单例的,你每次都是在从你的broker中拿连接,但原来你这个单例中如果持有另外的connection,则那个connection在没有关闭的情况下成了无主废人。

3.如果不是单例的,那么broker就被创建多次,我不知道你这个broker是个什么,但如果是连接池,那么每个新的实例会占用你initConnection中设置的数量的连接。



不错,还有在异常处理中,最好也调用你得connClose();
0 请登录后投票
论坛首页 入门技术版

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