Object

1. @HotSpotIntrinsicCandidate

@HotSpotIntrinsicCandidate
public final native Class<?> getClass();

使用@HotSpotIntrinsicCandidate注解标注的方法,表示JVM可能为该方法提供了一些基于CPU指令的高效实现,而非使用Java的实现。

2. native方法

getClass()hashCode()clone()notify()等方法的默认实现都是native方法

3. equals方法

equals()方法默认实现

public boolean equals(Object obj) {
return (this == obj);
}

4. clone方法

clone()方法默认是native实现,且默认是一个浅拷贝。但要调用这个方法,要求类实现Clonable接口,否则会抛出CloneNotSupportedException异常。即使Clonable没有定义任何方法。

public interface Cloneable {
}

下面是一个简单的示例

public class Test implements Cloneable{
public int a = 10; public static void main(String[] args) {
try {
Test test = new Test();
Object clone = test.clone();
System.out.println(clone.getClass());
System.out.println(test.getClass());
System.out.println(test.a);
Test toClone = (Test)clone;
System.out.println(toClone.a);
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
}
}
// 输出
class Test
class Test
10
10

6. toString方法

public String toString() {
return getClass().getName() + "@" + Integer.toHexString(hashCode());
}

默认实现返回类名+十六进制哈希码

7. notify和notifyAll方法

唤醒在对象监视器上等待的线程。

有下面这些方法令当前线程获得一个对象的监视器

  • 执行synchronized方法
  • 执行synchronized块
  • 执行synchronized的静态方法(获得的是当前类的class对象的监视器)

8. wait方法

下面是一个带纳秒参数nano的wait方法

public final void wait(long timeoutMillis, int nanos) throws InterruptedException {
if (timeoutMillis < 0) {
throw new IllegalArgumentException("timeoutMillis value is negative");
} if (nanos < 0 || nanos > 999999) {
throw new IllegalArgumentException(
"nanosecond timeout value out of range");
} if (nanos > 0 && timeoutMillis < Long.MAX_VALUE) {
timeoutMillis++;
} wait(timeoutMillis);
}

我们看到第三个if判断,假如nano参数大于0且timeoutMillis参数未满,所做的直接是令timeoutMillis参数自增。最后直接调用wait(timeoutMillis),这简直是对程序员的欺骗。注:1ms = 1000000ms

下面的这段代码是一段示例代码。推荐的等待方法是在调用wait的while循环中检查等待的条件,如下例所示。 这种方法避免了可能由虚假唤醒引起的问题。

虚假唤醒:线程可以在没有被通知、中断或超时的情况下唤醒

synchronized (obj) {
while (<condition does not hold> and <timeout not exceeded>) {
long timeoutMillis = ... ; // recompute timeout values
int nanos = ... ;
obj.wait(timeoutMillis, nanos);
}
... // Perform action appropriate to condition or timeout
}

9. finalize方法

@Deprecated(since="9")
protected void finalize() throws Throwable { }

显然我们看到,通过@Deprecated(since="9")注解,标记了finalize()方法自JDK9开始被弃用。

不推荐使用的原因

  • finalize()方法不能保证执行。

    还有另外一个方法能够回收对象,Runtime.getRuntime().runFinalization(); 但是这只能保证GC做出最大的努力,但是我们也不能finalize方法都能执行。我们还有一种方式能够保证执行finalize()方法,Runtime.runFinalizersOnExit(true),这个方法已经被JDK弃用,因为这种方法本质上是不安全的,可能导致finalizers方法被活对象调用而其他线程正在并行操作这个对象,从而导致不正确的行为或者死锁。

  • finalize()方法不像构造方法在链中工作,意味着像当你调用构造方法的时候,超类中的构造方法也会被隐含的调用,但是在finalize()方法的这种情况中,这种隐含的调用不会发生。超类中的finalize()方法需要显示的调用。假设,你创建了一个类并且小心翼翼的写了finalize()方法。一些人来extend了你的类,但是在子类中的finalize()块中没有调用super.finalize()方法。然后超类中finalize()方法将永远都不会被调用。

  • 任何有finalize()方法抛出的异常都会被GC线程忽略而且不会被进一步传播,事实上也不会在日志文件上记录下来。

正确的姿势

  • 要在finalize()方法中一直调用super.finalize()。
  • 考虑到不可预测预测性,不要在时间要求高的应用中使用finalize()。
  • 不要使用Runtime.runFinalizersOnExit(true);方法,因为你可能将你的系统置于危险之中。
  • 尝试遵循下边的模板使用finalize()方法。
@Override
protected void finalize() throws Throwable{
try{
//release resources here
}catch(Throwable t){
throw t;
}finally{
super.finalize();
}

JDK源码阅读:Object类阅读笔记的更多相关文章

  1. JDK源码之Integer类分析

    一 简介 Integer是int基本类型的包装类,同样继承了Number类,实现了Comparable接口,String类中的一些转化方法就使用了Integer类中的一些API,且fianl修饰不可继 ...

  2. 【java基础之jdk源码】Object

    最新在整体回归下java基础薄弱环节,以下为自己整理笔记,若有理解错误,请批评指正,谢谢. java.lang.Object为java所有类的基类,所以一般的类都可用重写或直接使用Object下方法, ...

  3. JDK源码之Double类&Float类分析

    一 概述 Double 类是基本类型double的包装类,fainl修饰,在对象中包装了一个基本类型double的值.Double继承了Number抽象类,具有了转化为基本double类型的功能. 此 ...

  4. JDK源码之String类解析

    一 概述 String由final修饰,是不可变类,即String对象也是不可变对象.这意味着当修改一个String对象的内容时,JVM不会改变原来的对象,而是生成一个新的String对象 主要考虑以 ...

  5. JDK源码之Byte类分析

    一 简介 byte,即字节,由8位的二进制组成.在Java中,byte类型的数据是8位带符号的二进制数,以二进制补码表示的整数 取值范围:默认值为0,最小值为-128(-2^7);最大值是127(2^ ...

  6. JDK源码之Boolean类分析

    一 简介 boolean类型的封装类,将基本类型为boolean的值包装在一个对象中,实现序列化接口,和Comparable接口 额外提供了许多便捷方法,比较简单,直接贴代码分析 二 源码分析 //t ...

  7. JDK源码之AbstractStringBuilder类分析

    一 概述 二 实现接口 AbstractStringBuilder实现了两个接口: Appendable 概述: Appendable的实现类的对象可以附加字符序列和值. 要追加的字符应该是Unico ...

  8. yii2 源码分析 object类分析 (一)

    转载请注明链接http://www.cnblogs.com/liuwanqiu/p/6737327.html yii2基本上所有的类都是继承的object类,下面就来分析一下object类吧 obje ...

  9. 源码学习-Object类

    1.Object类是Java所有类的超类 2.查看Object的属性和方法,发现Object类没有属性,只有13个方法,其中7个本地方法. 3.接下来看具体的方法 3.1 Object() 默认的构造 ...

  10. jdk源码理解-String类

    String类的理解 简记录一下对于jdk的学习,做一下记录,会持续补充,不断学习,加油 1.String的hash值的计算方法. hash值的计算方法多种多样,jdk中String的计算方法如下,比 ...

随机推荐

  1. Python之replace()方法失效

    1.背景 Titanic存活率预测案例: # 读取数据 df_train = pd.read_csv("./data/train.csv") df_train.head() OUT ...

  2. 浅谈C#取消令牌CancellationTokenSource

    前言 相信大家在使用C#进行开发的时候,特别是使用异步的场景,多多少少会接触到CancellationTokenSource.看名字就知道它和取消异步任务相关的,而且一看便知大名鼎鼎的Cancella ...

  3. CMMI相关图书

    Integrating CMMI and Agile Development: Case Studies and Proven Techniques for Faster Performance Im ...

  4. IllegalArgumentException occurred while calling setter for property

    参考https://blog.csdn.net/qq_41192690/article/details/80659427 主码 是 integer类型的 就不要在写成这个样子了 把type=" ...

  5. CleanArchitecture Application代码生成插件-让程序员告别CURD Ctrl+C Ctrl+V

    这是一个根据Domain项目中定义的实体对象(Entity)生成符合Clean Architecture原则的Application项目所需要的功能代码,包括常用的Commands,Queries,V ...

  6. jupyter notebook使用python虚拟环境

    jupyter指定环境启动 背景 系统环境中安装有jupyter及相关库,因项目需要,新建了一个torch相关的虚拟环境并安装了对应的内容, 此时,想通过系统中的jupyter启动一个可以应用虚拟环境 ...

  7. 安全工具推荐之w13scan篇

    先上链接:https://github.com/w-digital-scanner/w13scan 这是一款漏洞发现工具,支持三大主流平台:windows.Linux.Mac 又一款完全免费开源的工具 ...

  8. Flink项目实战(一)---核心概念及基本使用

    前言.flink介绍: Apache Flink 是一个分布式处理引擎,用于在无界和有界数据流上进行有状态的计算.通过对时间精确控制以及状态化控制,Flink能够运行在任何处理无界流的应用中,同时对有 ...

  9. DG:11.2.0.4 RAC在线duplicate恢复DG

    1.环境介绍 测试环境, 在一个双节点的RAC上使用duplicate搭建DG,使用在线的方式搭建 主机 IP 操作系统 实例 db_name db_unique_name db_version 配置 ...

  10. 超详细,自动化测试接入Jenkins+Sonar质量门禁实践

    大家好,我叫董鑫,一名在测试开发道路上的新手.第一阶段的学习已然结束,收获颇多,了解了很多在自己平时测试工作无法接触到的新知识,比如这次在这里分享的Sonarqube进行静态代码扫描并集成Jenkin ...