JDK源码

java.lang

object:

time:2020/10/7

1
2
3
4
Class {@code Object} is the root of the class hierarchy.
Every class has {@code Object} as a superclass. All objects,
including arrays, implement the methods of this class.
//Object类是类层次结构的根。Object是所有类的父类。所有对象,包括数组,都实现了这个类的方法。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
public class Object {
//初始化方法,一个静态块,一个静态方法和一个没有显示的默认构造方法,没有成员变量,可以看出来这个方法只会被调用一次
private static native void registerNatives();
//这里的native修饰,表示了这是java的原生态方法,方法对应的实现不是在当前文件,而是在用其他语言(如C和C++)实现的文件中,Java语言本身不能对操作系统底层进行访问和操作,但是可以通过JNI接口调用其他语言来实现对底层的调用
static {
registerNatives();
}
//getClass()方法被native修饰,告诉JVM自己去调用,同时也被final修饰,所以不能被子类重写,主要作用是返回正在运行的类别(Class)
public final native Class<?> getClass();
//hashCode()方法被native修饰,告诉JVM自己去调用,主要是返回对象的hashcode,主要是为了一些哈希表的数据结构服务的,在Java中hashcode与对象是否相等密切相关, 如果两个对象相等,则 hashcode 一定相等,但是 hashcode 相等,两个对象不一定相等。如果 hashcode 不相等,那么这两个对象一定不相等。
public native int hashCode();
//该方法是可以被重写的,主要用来判断两个对象是否相等,和自己相比返true,具有对称性、传递性与一致性,非空对象与null则返回false,比较为比较两个对象的内存地址,通常重写方法需要重写hashcode的方法
public boolean equals(Object obj) {
return (this == obj);
}
//该方法被native修饰,告诉 JVM 自己去调用。当我们在自定义类中使用该方法的时候,需要继承一个 Cloneable 接口,否则会抛出无法克隆的异常。该方法是一个浅复制,不是深复制(会创建新的对象)。
protected native Object clone() throws CloneNotSupportedException;
//notify() 随机唤醒一个等待线程,notifyAll() 唤醒全部的等待线程。wait() 方法让当前线程进入等待状态。无论当前线程调用哪个方法,都有一个前提:当前线程拥有对象的监视器。实现方法也很简单,配合 synchronized 关键字使用
public final native void notify();
public final native void notifyAll();
public final void wait() throws InterruptedException {
wait(0);
}
//实现方法:
synchronized (obj) {
while (true)
obj.wait();
// obj.notify();
}
//当垃圾回收器确定不再有对该对象的引用时,由垃圾回收器在对象上调用该方法。该方法只会被调用一次。
protected void finalize() throws Throwable { }
//让线程进入等待状态,传入时间(Long)
public final native void wait(long timeout) throws InterruptedException;
//wait(long timeout, int nanos)方法提供比wait(long timeout)更好的时间控制
public final void wait(long timeout, int nanos) throws InterruptedException {
if (timeout < 0) {
throw new IllegalArgumentException("timeout value is negative");
}
//nanos 单位为纳秒, 1毫秒 = 1000 微秒 = 1000 000 纳秒
if (nanos < 0 || nanos > 999999) {
throw new IllegalArgumentException(
"nanosecond timeout value out of range");
}
//这里有点奇怪,查阅了资料,目前结论为java中最小的时间单位还是毫秒,可能是由于操作系统做不到纳秒级别的精确度(或者是不需要精确到纳秒级别),因此jdk中做了一个近似处理的操作。
if (nanos > 0) {
timeout++;
}

wait(timeout);
}
}

string

time:2020/10/07

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
//方法被final修饰,定义以后不可改变不可重写,同时类不可被继承且线程安全,不用考虑线程安全问题,实现了Serializable,可被序列化被ObjectOutputStream转换为字节流,实现Comparable接口,CharSequence接口,能够做一些字符串操作,一般Stirng便可以取代CharSequence了
public final class String implements java.io.Serializable, Comparable<String>, CharSequence {
//定义存储字符类型的数组,即当使用String str = "abc";的时候,本质上,"abc"是存储在一个char类型的数组中的。
private final char value[];
//通过内存存储其哈希值
private int hash;
private static final long serialVersionUID = -6849794470754667710L;
//String的多种初始化方法
public String() {
this.value = "".value;
}
public String(String original) {
this.value = original.value;
this.hash = original.hash;
}
//String通过字符数组的实现,所以这些方法其实就是内部去调用数组的方法。
public String(char value[]) {
this.value = Arrays.copyOf(value, value.length);
}
public int length() {
return value.length;
}

public boolean isEmpty() {
return value.length == 0;
}

public char charAt(int index) {
if ((index < 0) || (index >= value.length)) {
throw new StringIndexOutOfBoundsException(index);
}
return value[index];
}
public String concat(String str) {
int otherLen = str.length();
if (otherLen == 0) {
return this;
}
int len = value.length;
char buf[] = Arrays.copyOf(value, len + otherLen);
str.getChars(buf, len);
return new String(buf, true);
}
public String replace(char oldChar, char newChar) {
if (oldChar != newChar) {
int len = value.length;
int i = -1;
char[] val = value; /* avoid getfield opcode */

while (++i < len) {
if (val[i] == oldChar) {
break;
}
}

if (i < len) {
char buf[] = new char[len];
//将老字符串遍历
for (int j = 0; j < i; j++) {
//第一个被匹配字符之前复制到新的字符串
buf[j] = val[j];
}
//从后面开始用三目运算判断替换存入新数组
while (i < len) {
char c = val[i];
buf[i] = (c == oldChar) ? newChar : c;
i++;
}
return new String(buf, true);
}
}
return this;
}
//bytes:需要转换成字符串的字节数组、offset:字节数组的第一个字节的下标、length:需要转换成字符串的字节长度、charset:编码格式的字符串名称,如:UTF-8
public String(byte bytes[], int offset, int length, Charset charset) {
if (charset == null)
throw new NullPointerException("charset");
checkBounds(bytes, offset, length);
this.value = StringCoding.decode(charset, bytes, offset, length);
}
}
//substring方法会创建一个新的String对象,将渊字符数组、需要剪切的数组起始坐标、长度传入
public String substring(int beginIndex, int endIndex) {
if (beginIndex < 0) {
throw new StringIndexOutOfBoundsException(beginIndex);
}
if (endIndex > value.length) {
throw new StringIndexOutOfBoundsException(endIndex);
}
int subLen = endIndex - beginIndex;
if (subLen < 0) {
throw new StringIndexOutOfBoundsException(subLen);
}
return ((beginIndex == 0) && (endIndex == value.length)) ? this
: new String(value, beginIndex, subLen);
}
//查询某个字符的位置
static int indexOf(char[] source, int sourceOffset, int sourceCount,
char[] target, int targetOffset, int targetCount,
int fromIndex) {
//判断查找的其实位置是否大于待查字符数组的长度
if (fromIndex >= sourceCount) {
return (targetCount == 0 ? sourceCount : -1);
}
//判断查找的位置是否小于0
if (fromIndex < 0) {
fromIndex = 0;
}
//如果待查找的字符为空则返回查找开始的位置
if (targetCount == 0) {
return fromIndex;
}
//得到待查找的字符数组第一个字符的ASCII码
char first = target[targetOffset];
//需要遍历的数目,这里判断了一下如果原数组长度还没有待查数组长的话就没有必要查找了直接返回-1
int max = sourceOffset + (sourceCount - targetCount);
//遍历原数组
for (int i = sourceOffset + fromIndex; i <= max; i++) {
/* Look for first character. */
//判断原字符数组中第一个与待查找的字符数组相同的字符
if (source[i] != first) {
while (++i <= max && source[i] != first);
}
/* Found first character, now look at the rest of v2 */
//循环判断原字符数组和待查找的字符数组后面的字符是否相等
if (i <= max) {
int j = i + 1;
int end = j + targetCount - 1;
//当不相等的时候不在循环
for (int k = targetOffset + 1; j < end && source[j]
== target[k]; j++, k++);
//当带查找数组遍历完之后
if (j == end) {
/* Found whole string. */
return i - sourceOffset;
}
}
}
return -1;
}

public String trim() {
int len = value.length;
int st = 0;
char[] val = value; /* avoid getfield opcode */
//定义双指针,如果遇到空格则首指针+1,尾指针-1。空格ASCII码为32
while ((st < len) && (val[st] <= ' ')) {
st++;
}
while ((st < len) && (val[len - 1] <= ' ')) {
len--;
}
return ((st > 0) || (len < value.length)) ? substring(st, len) : this;
}

}

AbstractStringBuilder

time: 2020/10/08

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
//抽象类定义,实现了两个接口,其中CharSequence为字符序列接口,Appendable接口顾名思义,定义添加的'规则'
abstract class AbstractStringBuilder implements Appendable, CharSequence {
//实际上存储也是字符数组,在这里与String的区别便是没有被final修饰,表示是可以被改变的
char[] value;
//实际存储的数量
int count;
//构造方法
AbstractStringBuilder() {
}
AbstractStringBuilder(int capacity) {
//给value赋值
value = new char[capacity];
}
//查询长度返回count值
public int length() {
return count;
}
//确保value数组的容量够用
public void ensureCapacity(int minimumCapacity) {
if (minimumCapacity > value.length) {
//如果不够用则会调用expandCapacity来为数组扩容
expandCapacity(minimumCapacity);
}
}
private void ensureCapacityInternal(int minimumCapacity) {
// overflow-conscious code
//这里对字符数组进行扩容,扩容容量便是传进来需要容量的参数,这里会新建立一个字符数组
if (minimumCapacity - value.length > 0) {
value = Arrays.copyOf(value,
newCapacity(minimumCapacity));
}
}
//这里为具体的扩容函数
private int newCapacity(int minCapacity) {
// overflow-conscious code
//首先新的容量为之前容量的两倍加2
int newCapacity = (value.length << 1) + 2;
//判断新的容量和需要的容量大小
if (newCapacity - minCapacity < 0) {
//如果新的容量还是小于需要的容量,则直接扩大需要的容量
newCapacity = minCapacity;
}
//如果新的容量小于0或者新的容量大于最大的容量调用hugeCapacity方法
return (newCapacity <= 0 || MAX_ARRAY_SIZE - newCapacity < 0)
//传入需要的容量
? hugeCapacity(minCapacity)
: newCapacity;
}

private int hugeCapacity(int minCapacity) {
//判断需要的容量是否超过了最大容量
if (Integer.MAX_VALUE - minCapacity < 0) { // overflow
//超过了的话则会抛出内存溢出异常
throw new OutOfMemoryError();
}
//如果需要的通量小于最大容量则会直接为最大容量
return (minCapacity > MAX_ARRAY_SIZE)
? minCapacity : MAX_ARRAY_SIZE;
}

public AbstractStringBuilder append(String str) {
//如果待拼接的字符串为null
if (str == null)
return appendNull();
int len = str.length();
//判断需要的容量会不会大于数组的容量
ensureCapacityInternal(count + len);
//得到待拼接字符串所有字符
str.getChars(0, len, value, count);
count += len;
return this;
}

public void getChars(int srcBegin, int srcEnd, char dst[], int dstBegin) {
//如果起点小于0,超出数组范围
if (srcBegin < 0) {
throw new StringIndexOutOfBoundsException(srcBegin);
}
//如果终点大于数组的长度,超出数组范围
if (srcEnd > value.length) {
throw new StringIndexOutOfBoundsException(srcEnd);
}
//如果起点大于终点
if (srcBegin > srcEnd) {
throw new StringIndexOutOfBoundsException(srcEnd - srcBegin);
}
//System中提供了一个native静态方法arraycopy(),可以使用这个方法来实现数组之间的复制。对于一维数组来说,这种复制属性值传递,修改副本不会影响原来的值。对于二维或者一维数组中存放的是对象时,复制结果是一维的引用变量传递给副本的一维数组,修改副本时,会影响原来的数组。
System.arraycopy(value, srcBegin, dst, dstBegin, srcEnd - srcBegin);
}

private AbstractStringBuilder appendNull() {
int c = count;
ensureCapacityInternal(c + 4);
final char[] value = this.value;
value[c++] = 'n';
value[c++] = 'u';
value[c++] = 'l';
value[c++] = 'l';
count = c;
return this;
}

private void ensureCapacityInternal(int minimumCapacity) {
// overflow-conscious code
//如果需要的容量大于value的长度,则会扩容
if (minimumCapacity - value.length > 0) {
value = Arrays.copyOf(value,
newCapacity(minimumCapacity));
}
}

public AbstractStringBuilder delete(int start, int end) {
//起点小于零则会抛出超出数组范围异常
if (start < 0)
throw new StringIndexOutOfBoundsException(start);
//中点大于数组长度则会直接赋值为数值长度
if (end > count)
end = count;
//起点大于终点抛异常
if (start > end)
throw new StringIndexOutOfBoundsException();
//需要删除的数组长度
int len = end - start;
if (len > 0) {
//System中提供了一个native静态方法arraycopy()
//创建一个一维空数组,然后将value源数组中 从start+len位到第count-end位之间的数值 copy 到 value目标数组中,在目标数组的第start位开始放置.
System.arraycopy(value, start+len, value, start, count-end);
count -= len;
}
return this;
}

public AbstractStringBuilder insert(int offset, String str) {
//放置的位置小于0或者大于数组长度
if ((offset < 0) || (offset > length()))
//内存溢出异常
throw new StringIndexOutOfBoundsException(offset);
if (str == null)
str = "null";
int len = str.length();
//检查数组容量是否足够
ensureCapacityInternal(count + len);
//System中提供了一个native静态方法arraycopy()
//将原数组的插入位置后面的字符向后移动len个位置
System.arraycopy(value, offset, value, offset + len, count - offset);
//将待复制的字符串填充进来
str.getChars(value, offset);
//长度增加
count += len;
return this;
}

//字符串元素替换
public AbstractStringBuilder replace(int start, int end, String str) {
//放置位置小于零,越界异常
if (start < 0)
throw new StringIndexOutOfBoundsException(start);、
//放置位置大于数组容量,越界异常
if (start > count)
throw new StringIndexOutOfBoundsException("start > length()");
//放置开始位置大于结束位置,越界异常
if (start > end)
throw new StringIndexOutOfBoundsException("start > end");
//放置结束位置大于容量位置,使用容量为其赋值
if (end > count)
end = count;
int len = str.length();
int newCount = count + len - (end - start);
//验证容量是否足够,不够将数组扩容
ensureCapacityInternal(newCount);
//System提供的方法
System.arraycopy(value, end, value, start + len, count - end);
//将待替换的字符数组插入
str.getChars(value, start);
//容量改变
count = newCount;
return this;
}

//字符串的反转,注意这里是在当前字符串数组里面进行操作的,并没有创建新的对象
public AbstractStringBuilder reverse() {
//是否含代理字符
boolean hasSurrogates = false;
//n为字符数组最后一位
int n = count - 1;
//将字符数组前后两个部分分别反过来赋值
for (int j = (n-1) >> 1; j >= 0; j--) {
int k = n - j;
//cj为前半部分,ck为后半部分
char cj = value[j];
char ck = value[k];
//反过来重新赋值
value[j] = ck;
value[k] = cj;
if (Character.isSurrogate(cj) ||
Character.isSurrogate(ck)) {
hasSurrogates = true;
}
}
if (hasSurrogates) {
reverseAllValidSurrogatePairs();
}
return this;
}
//反转回所有有效代理对
private void reverseAllValidSurrogatePairs() {
for (int i = 0; i < count - 1; i++) {
char c2 = value[i];
if (Character.isLowSurrogate(c2)) {
char c1 = value[i + 1];
if (Character.isHighSurrogate(c1)) {
value[i++] = c1;
value[i] = c2;
}
}
}
}
}

StringBuffer

time: 2020/10/09

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
//继承AbstractStringBuilder接口,实现Serializable与CharSequence,被final修饰不可重写不可改变,线程安全
public final class StringBuffer extends AbstractStringBuilder implements java.io.Serializable, CharSequence
{
//同样使用字符串数组进行操作
private transient char[] toStringCache;

static final long serialVersionUID = 3388685877147921107L;
//默认构造方法设置了value数组的初始容量为16。
public StringBuffer() {
super(16);
}
//第2个构造方法设置了value数组的初始容量为指定的大小。
public StringBuffer(int capacity) {
super(capacity);
}
//第3个构造方法接受一个String对象作为参数,设置了value数组的初始容量为String对象的长度+16,并把String对象中的字符添加到value数组中。
public StringBuffer(String str) {
super(str.length() + 16);
append(str);
}
//第4个构造方法接受一个CharSequence对象作为参数,设置了value数组的初始容量为CharSequence对象的长度+16,并把CharSequence对象中的字符添加到value数组中。
public StringBuffer(CharSequence seq) {
this(seq.length() + 16);
append(seq);
}

// AbstractStringBuilder.java
AbstractStringBuilder(int capacity) {
value = new char[capacity];
}
//这些常用的方法都是直接调用了父类抽象类AbstractStringBuilder的方法,但是注意这里的方法基本上都是被synchronized修饰的,所以是线程安全的
public synchronized StringBuffer append(String str) {
toStringCache = null;
super.append(str);
return this;
}

public synchronized StringBuffer replace(int start, int end, String str) {
toStringCache = null;
super.replace(start, end, str);
return this;
}

public synchronized void ensureCapacity(int minimumCapacity) {
super.ensureCapacity(minimumCapacity);
}

public synchronized StringBuffer delete(int start, int end) {
toStringCache = null;
super.delete(start, end);
return this;
}

public synchronized int indexOf(String str, int fromIndex) {
return super.indexOf(str, fromIndex);
}

public synchronized String substring(int start, int end) {
return super.substring(start, end);
}
}

StringBuilder

time: 2020/10/09

1
2
3
4
5
//继承AbstractStringBuilder接口,实现Serializable与CharSequence,被final修饰不可重写不可改变,线程不安全
public final class StringBuilder extends AbstractStringBuilder implements java.io.Serializable, CharSequence
{
//方法体内部基本上和StringBuffer一致,主要调用了父类AbstractStringBuilder的方法,但是没有被synchronized修饰,因此是线程不安全的
}

Boolean

time: 2020/10/10

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
//Boolean类,继承Serializable与Comparable接口,被final修饰,不能被继承,实现Comparable接口是为了方便在集合中进行比较,它需要实现的方法为compareTo
public final class Boolean implements java.io.Serializable,Comparable<Boolean>{
//保存boolean的值,被final修饰,表明是不可变的
private final boolean value;
public static final Boolean TRUE = new Boolean(true);
public static final Boolean FALSE = new Boolean(false);
public static final Class<Boolean> TYPE = (Class<Boolean>) Class.getPrimitiveClass("boolean");

//构造方法,Boolean类的两种构造函数可分别传入boolean和String类型
public Boolean(boolean value) {
this.value = value;
}
//对于String类型的值会进行”parseBoolean”解析,即当传入的字符串忽略大小写等于”true”时判断为true,否则为false
public Boolean(String s) {
this(parseBoolean(s));
}
public static boolean parseBoolean(String s) {
return ((s != null) && s.equalsIgnoreCase("true"));
}
//返回对象的boolean值
public boolean booleanValue() {
return value;
}
//valueOf方法,传入boolean或者String,用于返回boolean对象
public static Boolean valueOf(boolean b) {
return (b ? TRUE : FALSE);
}
public static Boolean valueOf(String s) {
return parseBoolean(s) ? TRUE : FALSE;
}

//可传入boolean类型或不传,传入boolean类型true时返回1231,false返回1237。不传时会调用此对象的Boolean.hashCode。
public int hashCode() {
return Boolean.hashCode(value);
}
public static int hashCode(boolean value) {
return value ? 1231 : 1237;
}

//先判断对象是否是Boolean类型,如果是再比较它们的值是否相等,否直接返回false
public boolean equals(Object obj) {
if (obj instanceof Boolean) {
return value == ((Boolean)obj).booleanValue();
}
return false;
}

//compareTo是实现的Comparable接口中的方法调用了compare方法,该方法返回0表示本对象与传入的对象相等,返回正数表示本对象比传入的对象大,返回负数表示本对象比传入的对象小。
public int compareTo(Boolean b) {
return compare(this.value, b.value);
}
//compare用于比较两个布尔值的大小,true大于false,如果相等返回0,如果不等当x为true,y为false时返回1,否则返回-1。
public static int compare(boolean x, boolean y) {
return (x == y) ? 0 : (x ? 1 : -1);
}

//三种逻辑运算
public static boolean logicalAnd(boolean a, boolean b) {
return a && b;
}
public static boolean logicalOr(boolean a, boolean b) {
return a || b;
}
public static boolean logicalXor(boolean a, boolean b) {
return a ^ b;
}
}

Byte

time: 2020/10/10

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67

public final class Byte extends Number implements Comparable<Byte> {

//byte 数据类型是8位、有符号的,以二进制补码表示的整数:最小值 -2^7
public static final byte MIN_VALUE = -128;
//byte 数据类型是8位、有符号的,以二进制补码表示的整数:最大值 2^7-1。
public static final byte MAX_VALUE = 127;

@SuppressWarnings("unchecked")
public static final Class<Byte> TYPE = (Class<Byte>) Class.getPrimitiveClass("byte");

public static String toString(byte b) {
//按十进制数处理
return Integer.toString((int)b, 10);
}

//静态内部类,缓存使用
private static class ByteCache {
private ByteCache(){}
//缓存数组的容量,长度为 128(负数) + 127(正数) + 1(0)
static final Byte cache[] = new Byte[-(-128) + 127 + 1];
//缓存初始化,范围是-128到127
static {
for(int i = 0; i < cache.length; i++)
cache[i] = new Byte((byte)(i - 128));
}
}

//推荐使用此方法进行构造Byte对象,从缓存中获取初始化好的Byte实例
public static Byte valueOf(byte b) {
final int offset = 128;
return ByteCache.cache[(int)b + offset];
}

//将字符串解析为byte类型,radix是基数,radix是几,s就是解析为几进制数
public static byte parseByte(String s, int radix)
throws NumberFormatException {
int i = Integer.parseInt(s, radix);
//判断超过大小限制
if (i < MIN_VALUE || i > MAX_VALUE)
throw new NumberFormatException(
"Value out of range. Value:\"" + s + "\" Radix:" + radix);
return (byte)i;
}
//默认为10进制数
public static byte parseByte(String s) throws NumberFormatException {
return parseByte(s, 10);
}

//实现Number父类的数据类型方法,直接强转
public byte byteValue() {return value;}
public short shortValue() {return (short)value;}
public int intValue() {return (int)value;}
public long longValue() { return (long)value;}
public float floatValue() {return (float)value;}
public double doubleValue() {return (double)value;}

//Byte比较大小
public int compareTo(Byte anotherByte) {
return compare(this.value, anotherByte.value);
}

public static int compare(byte x, byte y) {
//这里是直接相减,如果Integer使用减法可能可能会导致溢出,但其不会发生在Byte.compare的情况下,因为在计算x-y之前,字节值被隐式地转换为整数。
return x - y;
}
}