JAVA源码之JDK(一)——java.lang.Object
想要深入学习JAVA,还需追本溯源,从源码学起。这是我目前的想法。如今JAVA各种开源框架涌出,很多JAVA程序员都只停留在如何熟练使用的层次。身为其中一员的我深感惭愧,所以要加快学习的脚步,开始研究源码。希望这个系列我可以坚持下去。
JAVA程序员都知道Object是所有类的父类,所以,今天就从Object开始记录我的源码之路。
网上有很多关于Object类的详解,这里我只总结一点我所学到的,算是做个记录吧。
首先要看Object.class中的几个方法:
private static native void registerNatives();
public native int hashCode();
public boolean equals(Object obj) {
return (this == obj);
}
protected native Object clone() throws CloneNotSupportedException;
public String toString() {
return getClass().getName() + "@" + Integer.toHexString(hashCode());
}
public final native void notify();
public final native void wait(long timeout) throws InterruptedException;
protected void finalize() throws Throwable {}//空的方法
话说在这之前我还不知道native关键字是什么意思。下面是我的总结:
native
- native用来修饰方法(Method),表示是另外一种语言实现的本地方法。看上去更像是一个调用非JAVA语言写的方法的接口。【JNI(Java native interface):JAVA本机接口】
- native方法可以和除了abstract的任何JAVA方法修饰符一起使用,如static、synchronized等。【例Object类中的registerNatives(),不能与abstract一起使用的原因可以猜得到:native有实现】
- native方法的实现中可以访问JAVA特性,返回值也可以是一个JAVA类。【但是会很麻烦,
FindClass()获取类、
】GetMethodId()获取方法、CallVoidMethod()调用方法等等,但一般这么调用效率较低,可尽可能用字节数组。
- native方法可以被继承、可以抛异常等等。【与一个普通JAVA方法没什么两样。】
native方法存在的意义【只是我粗浅的理解】
JAVA语言是不能实现对操作系统底层的控制,这是为了让JAVA可以跨平台【不同的操作系统实现方式是不同的嘛】。这时候就要借助其它语言实现后,就可以通过JNI调用,就是这些native方法。其实这也就是JAVA跨平台的原理:使用其它语言【C\C++】针对不同操作系统写出不同的代码而实现同样的功能【如对内存、I/O的访问】,例如Object类中的notify()
、wait(long timeout),对于不同的操作系统调用不同的C语言的实现代码。
网上找的native方法的用处:
- 与旧有代码集成,避免重新编写。
- 实现可用类库中所缺少的功能。举例来说,在 Java 语言中实现
ping
时,您可能需要 Internet Control Message Protocol (ICMP) 功能,但基本类库并未提供它。- 最好与使用 C/C++ 编写的代码集成,以充分发掘性能或其他与环境相关的系统特性。
- 解决需要非 Java 代码的特殊情况。举例来说,核心类库的实现可能需要跨包调用或者需要绕过其他 Java 安全性检查。
native方法的简单实现
基本有如下步骤,我自己没实现过,只是用于大致了解和记忆:
- 在JAVA中声明native Method;
- 用javah命令产生一个.h文件;
- 用C语言(C++)写.c文件(.cpp),其中要#include "CheckFile.h"和#include "jni.h"【虽然我没有看过jni.h,但猜测是声明或实现了
FindClass()
这种可以与JAVA交互的方法】; - 将.c\.cpp文件生成.dll文件(动态链接库文件)。
- 在JAVA中用System.loadLibrary()方法加载.dll文件,这个native方法就可以在JAVA中被访问了。
关于native就到此为止,这有一篇关于JNI的文章:http://www.ibm.com/developerworks/cn/java/j-jni/
Object类中还有一些其它方法,如hashCode()和equals()这对组合。hash是一种程序员必须有的思想,具体会在后面HashMap的学习中详细记录,这里只写JDK的API上的解释:
- equals 方法体很简单,return (this == obj); 可以简单的理解为地址相同,下面是来自API的描述:
equals
方法在非空对象引用上实现相等关系:
- 自反性:对于任何非空引用值
x
,x.equals(x)
都应返回true
。- 对称性:对于任何非空引用值
x
和y
,当且仅当y.equals(x)
返回true
时,x.equals(y)
才应返回true
。- 传递性:对于任何非空引用值
x
、y
和z
,如果x.equals(y)
返回true
,并且y.equals(z)
返回true
,那么x.equals(z)
应返回true
。- 一致性:对于任何非空引用值
x
和y
,多次调用 x.equals(y) 始终返回true
或始终返回false
,前提是对象上equals
比较中所用的信息没有被修改。- 对于任何非空引用值
x
,x.equals(null)
都应返回false
。
Object
类的 equals 方法实现对象上差别可能性最大的相等关系;即,对于任何非空引用值x
和y
,当且仅当x
和y
引用同一个对象时,此方法才返回true
(x == y
具有值true
)。注意:当此方法被重写时,通常有必要重写 hashCode 方法,以维护 hashCode 方法的常规协定,该协定声明相等对象必须具有相等的哈希码。
- hashCode 可以简单的认为返回的是对象的地址,但实际是经过一个算法处理成一个整数的。
hashCode
的常规协定是:
- 在 Java 应用程序执行期间,在对同一对象多次调用 hashCode 方法时,必须一致地返回相同的整数,前提是将对象进行 equals 比较时所用的信息没有被修改。从某一应用程序的一次执行到同一应用程序的另一次执行,该整数无需保持一致。
- 如果根据 equals(Object) 方法,两个对象是相等的,那么对这两个对象中的每个对象调用
hashCode
方法都必须生成相同的整数结果。- 如果根据
equals(java.lang.Object)
方法,两个对象不相等,那么对这两个对象中的任一对象上调用 hashCode 方法不 要求一定生成不同的整数结果。但是,程序员应该意识到,为不相等的对象生成不同整数结果可以提高哈希表的性能。
剩下的方法这里就不再赘述了,因为回到文章的主题是想学习源码,而java.lang.Object类实际并没有什么源码【都是native方法用其它语言实现的】,所以诸如clone()的浅拷贝、深拷贝,以及多线程相关等等一开始学JAVA的时候都学过的,都留给平时去应用吧。
好了,关于源码的第一篇文章就到这里吧,还是开始提到的,希望我可以将这个系列坚持下去。
JAVA源码之JDK(一)——java.lang.Object的更多相关文章
- JAVA源码之JDK(二)——Integer、Long、Double
这篇文章继续java.lang包下的源码学习,笔者也是找了几个比较常用的来阅读.下面针对Integer.Long.Double这样的基本类型的封装类,记录一些比较经典.常用的方法的学习心得,如toSt ...
- JAVA源码之JDK(三)——String、StringBuffer、StrinBuilder
Java中,除了8种基本类型,最长用的应该就是String类了.那么我们来看看JDK中的源码是怎么建造String.StringBuffer.StrinBuilder一系列类的. java.lang. ...
- Java源码系列2——HashMap
HashMap 的源码很多也很复杂,本文只是摘取简单常用的部分代码进行分析.能力有限,欢迎指正. HASH 值的计算 前置知识--位运算 按位异或操作符^:1^1=0, 0^0=0, 1^0=0, 值 ...
- Java源码系列1——ArrayList
本文简单介绍了 ArrayList,并对扩容,添加,删除操作的源代码做分析.能力有限,欢迎指正. ArrayList是什么? ArrayList 就是数组列表,主要用来装载数据.底层实现是数组 Obj ...
- Java 源码学习线路————_先JDK工具包集合_再core包,也就是String、StringBuffer等_Java IO类库
http://www.iteye.com/topic/1113732 原则网址 Java源码初接触 如果你进行过一年左右的开发,喜欢用eclipse的debug功能.好了,你现在就有阅读源码的技术基础 ...
- 一点一点看JDK源码(二)java.util.List
一点一点看JDK源码(二)java.util.List liuyuhang原创,未经允许进制转载 本文举例使用的是JDK8的API 目录:一点一点看JDK源码(〇) 1.综述 List译为表,一览表, ...
- 一点一点看JDK源码(三)java.util.ArrayList 前偏
一点一点看JDK源码(三)java.util.ArrayList liuyuhang原创,未经允许禁止转载 本文举例使用的是JDK8的API 目录:一点一点看JDK源码(〇) 1.综述 ArrayLi ...
- 一点一点看JDK源码(四)java.util.ArrayList 中篇
一点一点看JDK源码(四)java.util.ArrayList 中篇 liuyuhang原创,未经允许禁止转载 本文举例使用的是JDK8的API 目录:一点一点看JDK源码(〇) 1.综述 在前篇中 ...
- 一点一点看JDK源码(五)java.util.ArrayList 后篇之forEach
一点一点看JDK源码(五)java.util.ArrayList 后篇之forEach liuyuhang原创,未经允许禁止转载 本文举例使用的是JDK8的API 目录:一点一点看JDK源码(〇) 代 ...
随机推荐
- mongod启动时候几个参数说明
1.--storageEngine从3.0开始,新增了一个存储引擎WT.老版本的存储引擎被称作mmapv1 2.--oplogSizeOplog是复制的主要组成部分,位于local数据库中.在初始化复 ...
- 开启ss-libev多用户
原理:通过查看进程,得到命令及需要的参数,然后,在制作一个配置文件,pid文件随意写. 1.首先正常开启一个: /etc/init.d/shadowsocks-libev start 2.然后:利用查 ...
- Atitit.遍历图像像素点rgb java attilax总结
Atitit.遍历图像像素点rgb java attilax总结 1. 遍历像素点 1 2. 提取一行 1 3. Rgb分量提取 2 4. 其他读取像素 3 5. --code 5 6. 参考 6 1 ...
- Atitit.ati orm的设计and架构总结 适用于java c# php版
Atitit.ati orm的设计and架构总结 适用于java c# php版 1. Orm的目标1 1.1. 动态obj1 1.2. Hb的api(meger,save,update,del)1 ...
- jsp的页面包含——静态包含、动态包含
一.静态包含:包含的文件可以是jsp文件.html文件.文本文件或者一段java代码.<%@ include file="要包含的文件路径"%> 实质是先将所包含的文件 ...
- root-me web server 10-20 writeup
File upload - double extensions文件上传--双扩展 Gallery v0.02 介绍 Your goal is to hack this photo galery by ...
- 【批量加入】-拼接sql字符串
如今做的一个项目须要用到批量加入,可是封装的底层没有这种方法,所以自食其力,自己来写.我们用的是拼接sql字符串的方法来实现功能. 详细实现流程:首先将须要的数据存储到实体的list中,然后将这个li ...
- shell 颜色
PS1='\[\e[33;1m\][\u@\h \W]\\$ \[\e[m\]' echo -e "\033[30m 黑色字oldboy trainning \033[0m" ec ...
- Java 使用 HttpClient调用https 最新源码 JDK7+ apache4.3+
在项目使用https方式调用别人服务的时候,以前要写很多的代码,现在框架封装了很多,所以不用再写那么多了. 网上看了一下,都是很老的版本,用过时的DefaultHttpClient. 以spring为 ...
- 微信抢红包微信 PHP代码实现
header("Content-Type: text/html;charset=utf-8");//输出不乱码,你懂的 $total=10;//红包总额 $num=8;// 分成8 ...