java 中的引用类型
1、强引用类型
2、弱引用
3、软引用
我们来举例说明下
package www.weiyuan.test; import java.lang.ref.SoftReference; import java.lang.ref.WeakReference; public class Test { public static void main(String[] args) { // TODO Auto-generated method stub
//创建了一个强引用类型 String str = "abc"; //创建一个软引用对象 SoftReference<String> sfr = new SoftReference<String>(str); //创建一个弱引用类型 WeakReference<String> wrf = new WeakReference<String>(str); } }
对象的可及性:一个对象可由多个变量来来引用,对象的可及性由最强引用类型来决定
上面对象adc有三个引用,一个是强可及,一个是软可及,还有一个是弱可及,最强引用是强可及
强可及对象永远不会被gcc垃圾回收器回收
软可及对象当系统内存不足的时候,gcc会把软可及对象回收掉
弱可及对象当gcc发现这个对象是弱可及对象就马上将对象回收
package www.weiyuan.test; import java.lang.ref.SoftReference; import java.lang.ref.WeakReference; public class Test { public static void main(String[] args) { // TODO Auto-generated method stub String str = "abc"; //创建一个软引用对象 SoftReference<String> sfr = new SoftReference<String>(str); //创建一个弱引用类型 WeakReference<String> wrf = new WeakReference<String>(str); //去除强可及str对象不再和adc对象存在任何关系 str = null; //通过软可及获得对象的值 String result1 = sfr.get(); //通过弱可及获得对象的值 String result2 = wrf.get(); System.out.println("result1 ="+result1); System.out.println("result2 ="+result1); } }
输出的结果是:
result1 =abc
result2 =abc
str = null;就是去掉str和对象"abc"的强可及关系,此时依然可以通过软引用和弱引用获得对象所关联的值
弱可及对象当gcc发现这个对象是弱可及对象就马上将对象回收
package www.weiyuan.test; import java.lang.ref.SoftReference; import java.lang.ref.WeakReference; public class Test { public static void main(String[] args) { // TODO Auto-generated method stub String str = "abc"; //创建一个软引用对象 SoftReference<String> sfr = new SoftReference<String>(str); //创建一个弱引用类型 WeakReference<String> wrf = new WeakReference<String>(str); //去除强可及str对象不再和adc对象存在任何关系 str = null; //清除软引用的引用链 sfr.clear(); //通过弱可及获得对象的值 String result2 = wrf.get(); //通过软可及获得对象的值 String result1 = sfr.get(); System.out.println("result1 ="+result1); System.out.println("result2 ="+result2); } }
我们使用
sfr.clear();去掉对象的软引用链接,这个时候对象的可及性是弱引用对象,清除之后通过软引用我们无法获得对象的值,但是依然可以通过弱引用获得对象的值,我们来看日志的打印输出
result1 =null
result2 =abc
在上面代码的基础上,我们知道当前对象的可及性是弱引用,我们收到调用gcc回收,看能否在获得对象的值
package www.weiyuan.test; import java.lang.ref.SoftReference; import java.lang.ref.WeakReference; public class Test { public static void main(String[] args) { // TODO Auto-generated method stub String str = "abc"; //创建一个软引用对象 SoftReference<String> sfr = new SoftReference<String>(str); //创建一个弱引用类型 WeakReference<String> wrf = new WeakReference<String>(str); //去除强可及str对象不再和adc对象存在任何关系 str = null; //清除软引用的引用链 sfr.clear(); //运行垃圾回收器 System.gc(); //通过弱可及获得对象的值 String result2 = wrf.get(); //通过软可及获得对象的值 String result1 = sfr.get(); System.out.println("result1 ="+result1); System.out.println("result2 ="+result2); } }
该对象已经是弱引用了,我们调用了系统的垃圾回收器,发现对象如果是弱引用,就立刻回收该对象的值
我们来看看日志的打印
result1 =null
result2 =abc
居然在垃圾回收器之后,居然还可以通过弱引用获得对象的值
这是为啥了,这里因为埋了一个坑
因为创建的对象
"abc"是存在在系统的常量池中的,我们使用gc是无法回收常量池中的对象的,gc只能回收堆内存中的弱引用对象
我们把
package www.weiyuan.test; import java.lang.ref.SoftReference; import java.lang.ref.WeakReference; public class Test { public static void main(String[] args) { // TODO Auto-generated method stub String str = new String("abc"); //创建一个软引用对象 SoftReference<String> sfr = new SoftReference<String>(str); //创建一个弱引用类型 WeakReference<String> wrf = new WeakReference<String>(str); //去除强可及str对象不再和adc对象存在任何关系 str = null; //清除软引用的引用链 sfr.clear(); //运行垃圾回收器 System.gc(); //通过弱可及获得对象的值 String result2 = wrf.get(); //通过软可及获得对象的值 String result1 = sfr.get(); System.out.println("result1 ="+result1); System.out.println("result2 ="+result2); } }
我们运行下代码:
result1 =null
result2 =null
通过new String的对象都是存在在堆内存中,所以我们使用gc就能够回收了。
posted on 2017-07-20 13:34 luzhouxiaoshuai 阅读(201) 评论(0) 编辑 收藏 举报
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!