对 java.lang 的研究

1、java.lang 研究


本篇文章讨论那些由java.lang定义的类和接口。
正如你所知道的那样,java.lang被自动导入所有的程序。它所包含的类和接口对所有实际的Java程序都是必要的。它是Java最广泛使用的包。
java.lang包括了下面这些类:
BooleanLongStrictMath(Java2,1.3)
ByteMathString
CharacterNumberStringBuffer
ClassObjectSystem
ClassLoaderPackage(Java2)Thread
CompilerProcess>ThreadGroup
DoubleRuntimeThreadLocal(Java2)
Float>RuntimePermission(Java2)Throwable
>InheritableThreadLocal(Java2)SecurityManagerVoid
>Integer>Short>
另外还有两个由Character定义的类:Character.Subset和Character.UnicodeBlock,它们是在Java2中新增加的。
java.lang也定义了如下的接口:
?Cloneable
?Comparable
?Runnable
其中Comparable接口是在Java2中新增加的。
java.lang中的几个类包含了过时的方法,其中的大多数可以追溯到Java1.0。在Java2中仍然提供了这些方法,用于支持逐渐减少的老程序,而这些方法在新程序中不被推荐使用。大多数的过时方法出现在Java2之前,因此在这里不讨论这些方法。而在Java2中出现的那些过时的方法将被提及。
Java2也在java.lang包中增加了几个新的类和方法,这些新类和方法被说明如下。

  1. 1、简单类型包装器

在本书的第1部分,我们提到因为性能的原因,Java使用简单的类型,例如整型(int)和字符(char)。这些数据类型不是对象层次结构的组成部分。它们通过值传递给方法而不能直接通过引用传递。而且,也没有办法使两种方法对整型(int)引用同一实例(sameinstance)。有时需要对这些简单的类型建立对象表达式。例如在第15章中讨论的仅仅处理对象的枚举类;如果要将简单类型存储到这些类中的一个,需要在类中包装简单类型。为了满足这种需要,Java提供了与每一个简单类型相应的类。本质上,这些类在类中包装(wrap)简单类型。因此,它们通常被称作类型包装器(wrappers)。
  1. 1.1、Number

抽象类Number定义了一个由包装数字类型字节型(byte),短整型(short),整型(int),长整型(long),浮点型(float)和双精度型(double)的类实现的超类。Number有返回上面不同数字格式的对象值的抽象方法。也就是,doubleValue()方法返回双精度(double)值,floatValue()方法返回浮点(float)值等。这些方法如下:
bytebyteValue()
doubledoubleValue()
floatfloatValue()
intintValue()
longlongValue()
shortshortValue()
这些方法的返回值可以被舍入。
Number有6个具体的子类包含了6种数字类型的显式值:双精度型(Double),浮点型(Float),字节型(Byte),短整型(Short),整型(Integer)和长整型(Long)。
  1. 1.2、Double和Float

双精度(Double)和浮点(Float)分别是对类型double和类型float的浮点值的包装器。浮点(Float)构造函数如下所示:
Float(doublenum)
Float(floatnum)
Float(Stringstr)引发NumberFormatException异常
正如你所看到的,浮点(Float)对象可以由类型float或类型double的值创建。它们也能由浮点数的字符串表达式创建。
双精度(Double)构造函数如下:
Double(doublenum)
Double(Stringstr)引发NumberFormatException异常
双精度(Double)对象可以被双精度(double)值或包含了浮点值的字符串创建。
由浮点(Float)定义的方法在表14-1中列出。由双精度(Double)定义的方法在表14-2中列出。浮点(Float)和双精度(Double)都定义了下面的常数:
MAX_VALUE最大正值
MIN_VALUE最小正值
NaN非数字
POSITIVE_INFINITY正无穷
NEGATIVE_INFINITY负无穷
TYPE浮点(float)或双精度(double)的类(Class)对象
表1由Float定义的方法
方法描述
bytebyteValue()返回调用对象的值(字节型)
intcompareTo(Floatf)将调用对象的数值与f中的数值进行比较,如果两者相等,返回0。如果调用对象的值小于f的值,则返回负值。如果调用对象的值大于f的值,则返回正值(在Java2中新增加的)
intcompareTo(objectobj)当obj是类Float中的对象时,该方法与compareTo(Float)的功能相同。否则,引发一个ClassCastException异常(在Java2中新增加的)
doubledoubleValue()返回调用对象的值(双精度型)
booleanequals(ObjectFloatObj)如果float调用对象与FloatObj相等,则返回true。否则返回false
staticintfloatToIntBits(floatnum)返回与num相应的与IEEE兼容的单精度位模式
FloatfloatValue()返回调用对象的值(浮点型)
inthashCode()返回调用对象的散列值
staticfloatintBitsToFloat(intnum)返回由num指定的,与IEEE兼容的单精度位模式的等价浮点(float)值
intintValue()返回整型(int)形式的调用对象值
booleanisInfinite()如果调用对象包含有无穷大值,则返回true。否则返回false
staticbooleanisInfinite(floatnum)如果num指定了一个无穷大值,则返回true。否则返回false
booleanisNaN()如果调用对象中包含了非数字值,则返回true。否则返回false
staticbooleanisNaN(floatnum)如果num指定了一个非数字值,则返回true。否则返回false
longlongValue()返回调用对象的值(长整型)
staticfloatparseFloat(Stringstr)throwsNumberFormatException以10为基数,返回包含在由str指定的字符串中的数字的等价浮点值(在Java2中新增加的)
shortshortValue()返回调用对象值(短整型)
StringtoString()返回调用对象的等价字符串形式
staticStringtoString(floatnum)返回由num指定的值的等价字符串
staticFloatvalueOf(Stringstr)throwsNumberForamtException返回包含了由str中的字符串指定的值的float对象

表2由Double定义的方法
方法描述
bytebyteValue()返回调用对象的值(字节型)
intcompareTo(Doubled)将调用对象的值与d的数值进行比较。如果这两个值相等,则返回0。如果调用对象的数值小于d的数值,则返回负值。如果调用对象的数值大于d的数值,则返回正值(在Java2中新增加的)
IntcompareTo(Objectobj)如果obj属于类Double,其操作与compareTo(Double)相同。否则,引发一个ClassCastException异常(在Java2中新增加的)
staticlongdoubleToLongBits(doublenum)返回与num相应的与IEEE兼容的双精度位模式
doubledoubleValue()返回调用对象的值(双精度)
booleanequals(ObjectDoubleObj)如果double调用对象与DoubleObj相等,则返回true。否则,返回false
floatfloatValue()返回调用对象的值(浮点型)
inthashcode()返回调用对象的散列码
intintValue()返回调用对象的值(整型)
booleanisInfinite()如果调用对象包含了一个无穷大值,则返回true。否则,返回false
staticbooleanisInfinite(doublenum)如果num指定了一个无穷大值,则返回true。否则,返回false
booleanisNaN()如果调用对象包含了一个非数字值,则返回true。否则,返回false
staticbooleanisNaN(doublenum)如果num指定了一个非数字值,则返回true。否则,返回false
staticdoublelongBitsToDouble(longnum)返回由num指定的,与IEEE兼容的双精度位模式的双精度(double)等价值
longlongValue()返回调用对象的值(长整型)
staticdoubleparseDouble(Stringstr)throwsNumberFormatException以10为基数,返回包含在由str指定的字符串中的数字的等价双精度(double)形式(在Java2中新增加的)
shortshortValue()返回调用对象的值(短整型)
StringtoString()返回调用对象的等价字符串形式
StaticStringtoString(doublenum)返回由num指定的值的等价字符串形式
StaticDoublevalueOf(Stringstr)throwsNumberFormatException返回包含了由str中的字符串指定的值的double对象
在下面的例子中创建两个double对象--一个通过使用双精度(double)值实现,另一个通过传递一个可以被解析为双精度(double)的字符串来实现。
classDoubleDemo{
publicstaticvoidmain(Stringargs[]){
Doubled1=newDouble(3.14159);
Doubled2=newDouble("314159E-5");

System.out.println(d1+"="+d2+"->"+d1.equals(d2));
}
}
正如从下面的输出中可以看到的那样,如同通过equals()方法返回true,两种构造函数创建相同的双精度(double)实例。
3.14159=3.14159->true
理解isInfinite()和isNaN()
浮点(Float)和双精度(Double)提供了isInfinite()和isNaN()方法,这些方法会有助于操作两个特殊的双精度(double)和浮点(float)值,这些方法检验两个由IEEE浮点规范定义的独特的值:无穷和NaN(非具体数字)。当被检验的值为无穷大或无穷小值时,isInfinite()方法返回true。当被检验值为非数字时,isNaN()方法返回true。
在下面的例子中构造了两个Double对象;一个是无穷,另一个是非数字:
//DemonstrateisInfinite()andisNaN()
classInfNaN{
publicstaticvoidmain(Stringargs[]){
Doubled1=newDouble(1/0.);
Doubled2=newDouble(0/0.);

System.out.println(d1+":"+d1.isInfinite()+","+d1.isNaN());
System.out.println(d2+":"+d2.isInfinite()+","+d2.isNaN());
}
}
程序运行产生如下的输出:
Infinity:true,false
NaN:false,true

Byte,Short,Integer,和Long类分别是字节型(byte),短整型(short),整型(int)和长整型(long)整数类型的包装器。它们的构造函数如下:
Byte(bytenum)
Byte(Stringstr)引发一个NumberFormatException异常
Short(shortnum)
Short(Stringstr)引发一个NumberFormatException异常
Integer(intnum)
Integer(Stringstr)引发一个NumberFormatException异常
Long(longnum)
Long(Stringstr)引发一个NumberFormatException异常
正如你能看到的,这些对象可由数值或含有有效整数值的字符串创建。
由这些类定义的方法列在表14-3到表14-6中。正如你能看到的,它们定义方法以便从字符串解析整数和将字符串转换为整数。为方便起见,这些方法提供的变量可以用来指定radix,也称为基数。通常二进制(binary)的基数是2,八进制(octal)的基数是8,十进制(decimal)的基数是10,而十六进制(hexadecimal)的基数为16。
表3由Byte定义的方法
方法描述
bytebyteValue()返回调用对象值(字节型)
intcompareTo(Byteb)将调用对象的数值与b的数值进行比较。如果这两个数值相等,则返回0。如果调用对象的数值小于b的数值,则返回负值。如果调用对象的数值大于b的数值,则返回正值(在Java2中新增加的)
intcompareTo(Objectobj)如果obj属于类Byte,其操作与compareTo(Byte)相同。否则,引发一个ClassCastException异常(在Java2中新增加的)
staticBytedecode(Stringstr)throwsNumberFormatException返回一个包含了由str中的字符串指定的值的Byte对象
doubledoubleValue()返回调用对象值(双精度度型)
booleanequals(ObjectByteObj)如果Byte调用对象与ByteObj相等,则返回true。否则,返回false
floatfloatValue()返回调用对象值(浮点型)
inthashCode()返回调用对象的散列码
intintValue()返回调用对象值(整型)
longlongValue()返回调用对象值(长整型)
staticbyteparseByte(Stringstr)throwsNumberFormatException以10为基数,返回包含在由str指定的字符串中的数字的等价字节(byte)形式
staticbyteparseByte(Stringstr,intradix)throwsNumberFormatException以指定的基数(radix)为底,返回包含在由str指定的字符串中的数字的等价字节
shortshortValue()返回调用对象值(短整型)
StringtoString()返回一个包含了调用对象的等价十进制形式的字符串
staticStringtoString(bytenum)返回一个包含了num的等价十进制形式的字符串
staticBytevalueOf(Stringstr)throwsNumberFormatException返回一个包含了由str中的字符串指定的值的Byte对象
staticBytevalueOf(Stringstr,intradix)throwsNumberFormatException以指定的基数(radix)为底,返回一个包含了由str中的字符串指定的值的Byte对象
表4由Short定义的方法
方法描述
bytebyteValue()返回调用对象值(字节型)
intcompareTo(Shorts)将调用对象的数值和s的数值进行比较。如果这两个值相等,则返回0。如果调用对象的数值小于s的数值,则返回负值如果调用对象的数值大于s的数值,则返回正值(在Java2中新增加的)
intcompareTo(Objectobj)如果obj属于类Short,其操作与compareTo(Short)相同。否则,引发一个ClassCastException异常(在Java2中新增加的)
staticShortdecode(Stringstr)throwsNumberFormatException返回一个包含了由str中的字符串指定值的Short对象
doubledoubleValue()返回调用对象值(双精度型)
booleanequals(ObjectShortObj)如果整型(Interger)调用对象与ShortObj相等,则返回true。否则,返回false
floatfloatValue()返回调用对象值(浮点值)
inthashCode()返回调用对象的散列码
intintValue()返回调用对象值(整型)
longlongValue()返回调用对象值(长整型)
staticshortparseShort(Stringstr)throwsNumberFormatException以10为基数,返回包含在由str指定的字符串中的数字的等价短整型(Short)数
staticshortparseShort(Stringstr,intradix)throwsNumberFormatException以指定的基数(radix)为底,返回包含在由str指定的字符串中的数字的等价短整型(Short)数
shortshortValue()返回调用对象值(短整型)
StringtoString()返回一个包含了调用对象的等价十进制形式的字符串
staticStringtoString(shortnum)返回一个包含了num的等价十进制形式的字符串
staticShortvalueOf(Stringstr)throwsNumberFormatException以10为基数,返回一个包含了由str中的字符串指定的值的Short对象
staticShortvalueOf(Stringstr,intradix)throwsNumberFormatException以指定的基数(radix)为底,返回一个包含了由str中的字符串指定的值的Short对象
表5由Integer定义的方法
方法描述
bytebyteValue()返回调用对象值(字节型)
intcompareTo(Integeri)将调用对象的数值与i的数值进行比较。如果这两个值相等,则返回0。如果调用对象的数值小于i的数值,则返回负值。如果调用对象的数值大于i的数值,则返回正值(在Java2中新增加的)
intcompareTo(Objectobj)如果obj属于类Integer,其操作与compareTo(Integer)相同。否则,引发一个ClassCastException异常(在Java2中新增加的)
staticIntegerdecode(Stringstr)throwsNumberFormatException返回一个包含了由str中的字符串指定值的Integer对象
doubledoubleValue()返回调用对象值(双精度型)
booleanequals(ObjectIntegerObj)如果调用Interger对象与IntegerObj相等,则返回true。否则,返回false
floatfloatValue()staticIntegergetInteger(StringpropertyName)返回调用对象值(浮点型)返回与由propertyname指定的环境属性相关联的值,调用失败返回null
staticIntegergetInteger(StringpropertyName,intdefault)返回与由propertyname指定的环境属性相关联的值,调用失败返回default值
staticIntegergetInteger(StringpropertyName,Integerdefault)返回与由propertyname指定的环境属性相关联的值,调用失败返回default值
inthashCode()返回调用对象的散列码
intintValue()返回调用对象值(整型)
longlongValue()返回调用对象值(长整型)
staticintparseInt(Stringstr)throwsNumberFormatException以10为基数,返回包含在由str指定的字符串中的数字的等价整数(integer)值
staticintparseInt(Stringstr,intradix)throwsNumberFormatException以指定的基数(radix)为底,返回包含在由str指定的字符串中的数字的等价整数值
shortshortValue()返回调用对象值(短整型)
staticStringtoBinaryString(intnum)返回一个包含了num的等价二进制形式的字符串
staticStringtoHexString(intnum)返回一个包含了num的等价十六进制形式的字符串
staticStringtoOctalString(intnum)返回一个包含了num的等价八进制形式的字符串
StringtoString()返回一个包含了调用对象的等价十进制形式的字符串
staticStringtoString(intnum)返回一个包含了num的等价十进制形式的字符串
staticStringtoString(intnum,intradix)以指定的基数(radix)为底,返回一个包含了num的等价十进制形式的字符串
staticIntegervalueOf(Stringstr)throwsNumberFormatException返回一个包含了由str中的字符串指定的值的Integer对象
staticIntegervalueOf(Stringstr,intradix)throwsNumberFormatException以指定的基数(radix)为底,返回一个包含了由str中的字符串指定的值的Integer对象

表6由Long定义的方法
方法描述
bytebyteValue()返回调用对象值(字节型)
intcompareTo(Longl)将调用对象的数值和l的数值进行比较,如果这两个值相等,则返回0。如果调用对象的数值小于l的数值,则返回负值。如果调用对象的数值大于l的数值,则返回正值(在Java2中新增加的)
intcompareTo(Objectobj)如果obj属于类long,其操作与compareTo(Long)相同。否则,引发一个ClassCastException异常(在Java2中新增加的)
staticLongdecode(Stringstr)throwsNumberFormatException返回一个包含了由str中的字符串指定的值的Long对象
doubledoubleValue()返回调用对象值(双精度型)
booleanequals(ObjectLongObj)如果调用Long对象与LongObj相等,则返回true。否则,返回false
floatfloatValue()返回调用对象值(浮点型)
staticLonggetLong(Stringpropertyname)返回与由propertyname指定的环境属性相关联的值,调用失败则返回null
staticLonggetLong(Stringpropertyname,longdefault)返回与由propertyname指定的环境属性相关联的值,调用失败则返回default的值
staticlonggetLong(Stringpropertyname,Longdefault)返回与由propertyname指定的环境属性相关联的值,调用失败则返回default的值
inthashcode()返回调用对象的散列码
intintValue()返回调用对象值(整型)
longlongValue()返回调用对象值(长整型)
staticlongparseLong(Stringstr)throwsNumberFormatException以10为基数,返回包含在由str指定的字符串中的数字的等价长整型(Long)数
staticlongparseLong(Stringstr,intradix)throwsNumberFormatException以指定的基数(radix)为底,返回包含在由str指定的字符串中的数字的等价长整型(Long)数
shortshortValue()返回调用对象值(短整型)
staticStringtoBinaryString(longnum)返回一个包含了num的等价二进制形式的字符串
staticStringtoHexString(longnum)返回一个包含了num的等价十六进制形式的字符串
staticStringtoOctalString(longnum)返回一个包含了num的等价八进制形式的字符串
StringtoString()返回一个包含了调用对象的等价十进制形式的字符串
staticStringtoString(longnum)返回一个包含了num的等价十进制形式的字符串
staticStringtoString(longnum,intradix)以指定的基数(radix)为底,返回一个包含了num的等价十进制形式的字符串
staticLongvalueOf(Stringstr)throwsNumberFormatException返回一个包含了由str中的字符串指定的值的Long对象
staticLongvalueOf(Stringstr,intradix)throwsNumberFormatException以指定的基数(radix)为底,返回一个包含了由str中的字符串指定的值的Long对象
定义下面的常数:
MIN_VALUE最小值
MAX_VALUE最大值
TYPE字节(Byte),短整型(short),整型(int)或长整型(long)的类(Class)对象
数字和字符串的转换
程序设计中一个最常见的任务是将一个数字的字符串表达式转换成内部的二进制格式。幸运的是Java提供了一个方便的方法去完成这项任务。Byte,Short,Integer和Long类分别提供了parseByte(),parseShort(),parseInt()和parseLong()方法。这些方法返回与调用它们的数值字符串相应的字节(byte),短整型(short),整型(int)和长整型(long)值(在Float和Double类中也有相似的方法)。
下面的程序说明了parseInt()方法。该程序完成对用户输入的一系列整数的求和。在程序中通过使用readLine()方法读取整数,使用parseInt()方法将这些字符串转换成与之相应的整型(int)值。
/*Thisprogramsumsalistofnumbersentered
bytheuser.Itconvertsthestringrepresentation
ofeachnumberintoanintusingparseInt().
*/

importjava.io.*;

classParseDemo{
publicstaticvoidmain(Stringargs[])
throwsIOException
{
//createaBufferedReaderusingSystem.in
BufferedReaderbr=new
BufferedReader(newInputStreamReader(System.in));
Stringstr;
inti;
intsum=0;

System.out.println("Enternumbers,0toquit.");
do{
str=br.readLine();
try{
i=Integer.parseInt(str);
}catch(NumberFormatExceptione){
System.out.println("Invalidformat");
i=0;
}
sum+=i;
System.out.println("Currentsumis:"+sum);
}while(i!=0);
}
}
为了将一个整数转换为一个十进制的字符串,可以使用在Byte,Short,Integer或Long类中定义的toString()方法。Integer和Long类还同时提供了toBinaryString(),toHexString()和toOctalString()方法,可以分别将一个值转换成二进制,十六进制和八进制字符串。
下面的程序说明了向二进制,十六进制和八进制的转换:
/*Convertanintegerintobinary,hexadecimal,
andoctal.
*/
classStringConversions{
publicstaticvoidmain(Stringargs[]){
intnum=19648;

System.out.println(num+"inbinary:"+
Integer.toBinaryString(num));

System.out.println(num+"inoctal:"+
Integer.toOctalString(num));

System.out.println(num+"inhexadecimal:"+
Integer.toHexString(num));
}
}
程序的输出结果如下所示:
19648inbinary:100110011000000
19648inoctal:46300
19648inhexadecimal:4cc0
  1. 1.4、Character

字符(Character)是围绕字符型(char)的一个简单的包装器。字符(Character)的构造函数如下:
Character(charch)
这里ch指定了被创建的字符(Character)对象所包装的字符。
调用如下的charValue()方法可以获得包含在字符(Character)对象中的字符型(char)值。
charcharValue()
调用的结果返回字符。
字符(Character)类定义了几个常数,包括下面这些:
MAX_RADIX最大基数
MIN_RADIX最小基数
MAX_VALUE最大字符值
MIN_VALUE最小字符值
TYPE字符型(char)的类(Class)对象
字符(Character)包括了几个静态方法,这些方法完成将字符分类并改变它们的大小写。这些方法在表7中列出。下面的例子说明了这些方法。
//DemonstrateseveralIs...methods.

classIsDemo{
publicstaticvoidmain(Stringargs[]){
chara[]={'a','b','5','?','A',''};

for(inti=0;i<a.length;i++){
if(Character.isDigit(a[i]))
System.out.println(a[i]+"isadigit.");
if(Character.isLetter(a[i]))
System.out.println(a[i]+"isaletter.");
if(Character.isWhitespace(a[i]))
System.out.println(a[i]+"iswhitespace.");
if(Character.isUpperCase(a[i]))
System.out.println(a[i]+"isuppercase.");
if(Character.isLowerCase(a[i]))
System.out.println(a[i]+"islowercase.");
}
}
}
程序的输出结果如下所示:
aisaletter.
aislowercase.
bisaletter.
bislowercase.
5isadigit.
Aisaletter.
Aisuppercase.
iswhitespace.
表7各种字符(Character)方法
方法描述
staticbooleanisDefined(charch)如果ch是由Unicode定义的,则返回true,否则,返回false
staticbooleanisDigit(charch)如果ch是一个数字,则返回true,否则,返回false
staticbooleanisIdentifierIgnorable(charch)如果在一个标识符中ch应被忽略,则返回true,否则,返回false
staticbooleanisISOControl(charch)如果ch是一个ISO控制字符,则返回true,否则,返回false
staticbooleanisJavaIdentifierPart(charch)如果ch被做为Java标识符的一部分(除了第一个字符),则返回true。否则,返回false
staticbooleanisJavaIdentifierStart(charch)如果ch被做为Java标识符的首字符,则返回true。否则返回false
staticbooleanisLetter(charch)如果ch是一个字母,则返回true。否则返回false
staticbooleanisLetterOrDigit(charch)如果ch是一个字母或一个数字,则返回true。否则返回false
staticbooleanisLowerCase(charch)当ch是小写字母时,返回true。否则返回false
staticbooleanisSpaceChar(charch)如果ch是Unicode编码的空格字符,则返回true。否则返回false
staticbooleanisTitleCase(charch)如果ch是Unicode编码的标题字符,则返回true。否则返回false
staticbooleanisUnicodeIdentifierPart(charch)如果ch被做为Unicode编码标识符的一部分(除了第一个字符),则返回true。否则,返回false
staticbooleanisUnicodeIdentifierStart(charch)如果ch被做为一个Unicode标识符的首字符,则返回true。否则返回false
staticbooleanisUpperCase(charch)如果ch是一个大写字母,则返回true。否则返回false
staticbooleanisWhitespace(charch)如果ch是一个空白符,则返回true。否则,返回false
staticchartoLowerCase(charch)返回ch的小写等价形式
staticchartoTitleCase(charch)返回ch的标题等价形式
staticchartoUpperCase(charch)返回ch的大写等价形式
字符(Character)定义了如下形式的forDigit()和digit()方法:
staticcharforDigit(intnum,intradix)
staticintdigit(chardigit,intradix)
forDigit()方法返回与num的值关联的数字字符。而转换的基数由radix指定。digit()方法按照给定的基数,返回与指定字符(该字符可能是一个数字)相关联的整数值。
由Character类定义的另一个方法是compareTo(),该方法具有如下的两种形式:
intcompareTo(Characterc)
intcompareTo(Objectobj)
第一种形式当调用对象与c具有相同值时返回0。当调用对象具有比c小的值时返回一个负值。否则它将返回一个正值。在第二种形式中,当obj是对Character类的一个引用时,其功能与第一种形式一样。否则它将引发一个ClassCastException异常。这些方法是在Java2中新增加的。
Character类还定义了equals()和hashCode()方法。
另两个与字符有关的类是Character.Subset和Character.UnicodeBlock,其中Character.Subset类用于描述Unicode编码的一个子集,而Character.UnicodeBlock类中包含了Unicode2.0编码的字符块。
  1. 1.5、Boolean

Boolean是一个围绕布尔(boolean)值的非常细小的包装器,主要用在通过引用传递布尔(boolean)变量的场合。它包含了常数TRUE和FALSE,这些常数定义了布尔(Boolean)对象的真与假。Boolean也定义了TYPE域,它是boolean的Class对象。在Boolean中定义了如下的构造函数:
Boolean(booleanboolValue)
Boolean(StringboolString)
在第一种形式中,boolValue要么是true,要么是false。在第二种形式中,如果在boolString中包含了字符串“true”(无论是大写形式还是小写形式),则新的布尔(Boolean)对象将为真,否则为假。
Boolean定义了如表14-8中列出的方法。
表8由Boolean定义的方法
方法描述
booleanbooleanValue()返回布尔(boolean)等价形式
booleanequals(ObjectboolObj)如果调用对象与boolObj相等,则返回true。否则返回false
staticbooleangetBoolean(StringpropertyName)如果由propertyName指定的系统属性为true,则返回true。否则返回false
inthashCode()返回调用对象的散列码
StringtoString()返回调用对象的字符串等价形式
staticBooleanvalueOf(StringboolString)如果在boolString中包含了“true”(以大写或小写形式),则返回true。否则返回false
  1. 2、Void

Void类有一个TYPE域,该域保存对类型void的Class对象的引用。这样做将不创建类的实例。
  1. 3、Process

抽象类Process封装了一个进程(process)--也就是说一个正在执行的程序。它主要被当作由Runtime类中的exec()方法所创建的对象的类型的超类。Runtime类将在下面介绍。在抽象类Process中,包含了如下表14-9中列出的抽象方法。
表9由Process定义的抽象方法
方法描述
voiddestroy()中断进程
intexitValue()返回一个从子进程获得的退出码
InputStreamgetErrorStream()返回一个从进程的err输出流中读输入的输入流
InputStreamgetInputStream()返回一个从进程的out输出流中读输入的输入流
OutputStreamgetOutputStream()返回一个从进程的in输入流中写输出的输出流
IntwaitFor()throwsInterruptedException返回由进程返回的退出码。这个方法直到调用它的进程中止,才会返回
  1. 4、Runtime

Runtime类封装了运行时环境。一般不实例化一个Runtime对象。但是可以通过调用静态方法Runtime.getRuntime()而获得对当前Runtime对象的引用。一旦获得了对当前对象的引用,就可以调用几个控制Java虚拟机的状态和行为的方法。小应用程序(Applets)和其他不可信赖的编码由于没有引起一个安全异常(SecurityException)而不能调用任何的Runtime方法。
表10给出了由Runtime定义的方法。Java2中不赞成使用方法runFinalizersonExit()。这种方法是在Java1.1中增加的,但被认为是一种不稳定的方法。
表10由Runtime定义的常用方法
方法描述
voidaddShutdownHook(Threadthrd)当Java虚拟机终止时,寄存器thrd作为线程而运行
Processexec(StringprogName)throwsIOException将由progName指定的程序作为独立的进程来执行。返回描述新进程的类型Process的对象
Processexec(StringprogName,Stringenvironment[])throwsIOException将由progName指定的程序作为独立的进程来执行。该独立进程的环境由environment指定。返回描述新进程的类型Process的对象
Processexec(StringcomLineArray[],Stringenvironment[])throwsIOException将由comLineArray中的字符串指定的命令行作为独立的进程来执行。运行环境由environment指定。返回描述新进程的类型Process的对象
voidexit(intexitCode)暂停执行并且向父进程返回exitCode的值,按照约定,0表示正常中止,所有的其他值表示有某种形式的错误
longfreeMemory()返回Java运行系统可以利用的空闲内存的大概字节数
voidgc()初始化垃圾回收站
staticRuntimegetRuntime()返回当前的Runtime对象
voidhalt(intcode)立即终止Java虚拟机,不执行任何的终止线程和善后处理程序。code的值返回给调用进程(在Java2的1.3版中新增加的)
voidload(StringlibraryFileName)载入库中文件由libraryFileName指定的动态库,必须指定它的完全路径
voidloadLibrary(StringlibraryName)载入库名为libraryName的动态库
booleanremoveShutdownHook(Threadthrd)当Java虚拟机中止,从线程列表中移出thrd的运行。如果成功,也就是说如果线程被移出,则返回true(在Java2的1.3版中新增加的)
voidrunFinalization()调用未用的但还不是回收站中对象的finalize()方法
longtotalMemory()返回程序可以利用的内存的总字节数
voidtraceInstructions(booleantraceOn)根据traceOn的值,打开或关闭指令跟踪。如果traceOn值为true,跟踪被显示。如果traceOn值为false,跟踪被关闭
voidtraceMethodCalls(booleantraceOn)根据traceOn的值,打开或关闭调用跟踪的方法。如果traceOn的值为true,跟踪被显示。如果traceOn的值为false,跟踪被关闭
让我们来看一看Runtime类的两个最普遍的用法:内存管理和执行附加进程。
  1. 4.1内存管理

尽管Java提供了自动垃圾回收,有时也想知道对象堆的大小以及它还剩下多少。可以利用这些信息检验你的代码的效率,或估计对某些类型,有多少对象可以被实例化。为了获得这些值,可以使用totalMemory()和freeMemory()方法。
正如我们在第1部分提及的,Java的垃圾回收器周期性地运行将不再使用的对象放入回收站。然而有时想在收集器的下一个指定循环之前收集被丢弃的对象。可以通过调用gc()方法按照要求运行垃圾回收器。一个好的尝试是调用gc()方法,然后再调用freeMemory()方法以获得内存使用的底线。接着执行你的程序,并再一次调用freeMemory()方法看分配了多少内存。下面的例子说明了这个思想。
//DemonstratetotalMemory(),freeMemory()andgc().

classMemoryDemo{
publicstaticvoidmain(Stringargs[]){
Runtimer=Runtime.getRuntime();
longmem1,mem2;
Integersomeints[]=newInteger[1000];

System.out.println("Totalmemoryis:"+
r.totalMemory());

mem1=r.freeMemory();
System.out.println("Initialfreememory:"+mem1);
r.gc();
mem1=r.freeMemory();
System.out.println("Freememoryaftergarbagecollection:"
+mem1);

for(inti=0;i<1000;i++)
someints[i]=newInteger(i);//allocateintegers

mem2=r.freeMemory();
System.out.println("Freememoryafterallocation:"
+mem2);
System.out.println("Memoryusedbyallocation:"
+(mem1-mem2));

//discardIntegers
for(inti=0;i<1000;i++)someints[i]=null;

r.gc();//requestgarbagecollection

mem2=r.freeMemory();
System.out.println("Freememoryaftercollecting"+
"discardedIntegers:"+mem2);

}
}
这个例子的一个输出样本如下(当然,你的实际运行结果可能会与之不同):
Totalmemoryis:1048568
Initialfreememory:751392
Freememoryaftergarbagecollection:841424
Freememoryafterallocation:824000
Memoryusedbyallocation:17424
FreememoryaftercollectingdiscardedIntegers:842640
  1. 4.2、执行其他的程序


在可靠的环境中,可以在你的多任务操作系统中使用Java去执行其他特别繁重的进程(也即程序)。exec()方法的几种形式允许命名想运行的程序以及它们的输入参数。exec()方法返回一个Process对象,这个对象可以被用来控制你的Java程序如何与这个正在运行的新进程相互作用。因为Java可以运行在多种平台和多种操作系统的情况下,exec()方法本质上是依赖于环境的。
下面的例子使用exec()方法装入Window的简单文本编辑器--notepad。显而易见,这个例子必须在Windows操作系统下运行。
//Demonstrateexec().
classExecDemo{
publicstaticvoidmain(Stringargs[]){
Runtimer=Runtime.getRuntime();
Processp=null;

try{
p=r.exec("notepad");
}catch(Exceptione){
System.out.println("Errorexecutingnotepad.");
}
}
}
exec()方法有几个形式可用,而在本例子中展示的是最常用的一种。在新程序开始运行之后,由exec()方法返回的Process对象可以被Process方法使用。可以使用destroy()方法杀死子进程。waitFor()方法暂停你的程序直至子进程结束。当子进程结束后,exitValue()方法返回子进程返回的值。如果没有问题发生,它通常返回0。下面是前面关于exec()方法例子的改进版本。例子被修改为等待直至正在运行的进程退出:
//Waituntilnotepadisterminated.
classExecDemoFini{
publicstaticvoidmain(Stringargs[]){
Runtimer=Runtime.getRuntime();
Processp=null;

try{
p=r.exec("notepad");
p.waitFor();
}catch(Exceptione){
System.out.println("Errorexecutingnotepad.");
}
System.out.println("Notepadreturned"+p.exitValue());
}
}
当子进程正在运行时,可以从它的标准输入输出进行读和写。getOutputStream()方法和getInputStream()方法返回子进程的标准输入(in)和输出(out)的句柄。

  1. 5、System


System类保存静态方法和变量的集合。标准的输入,输出和Java运行时错误输出存储在变量in,out和err中。由System类定义的方法列在表14-11中。注意当所做操作是安全方式所不允许的时,许多方法引发一个安全异常(SecurityException)。应当注意的另一点是:Java2不赞成使用runFinalizersonExit()方法。该方法是在Java1.1中增加的,同时也被证明是不可靠的。
让我们看一看System类的一些普遍用法。
表11由Sysem定义的方法
方法描述
staticvoidarraycopy(Objectsource,intsourceStart,Objecttarget,inttargetStart,intsize)复制数组。被复制的数组由source传递,而source中开始复制数组时的下标由sourceStart传递。接收复制的数组由target传递。而target中开始复制数组时的下标由targetStart传递。Size是被复制的元素的个数
staticlongcurrentTimeMillis()返回自1970年1月1日午夜至今的时间,时间单位为毫秒。
staticvoidexit(intexitCode)暂停执行,返回exitCode值给父进程(通常为操作系统)。按照约定,0表示正常退出,所有其他的值代表某种形式的错误
staticvoidgc()初始化垃圾回收
staticPropertiesgetProperties()返回与Java运行系统有关的属性类(Propertiesclass)将在第15章中介绍)
staticStringgetProperty(Stringwhich)返回与which有关的属性。如果期望的属性没有被发现,返回一个空对象(nullobject)
staticStringgetProperty(Stringwhich,Stringdefault)返回一个与which有关的属性。如果期望的属性没有被发现,则返回default
staticSecurityManagergetSecurityManager()返回当前的安全管理程序,如果没有安装安全管理程序,则返回一个空对象(nullobject)
staticnativeintidentityHashCode(Objectobj)返回obj的特征散列码
staticvoidload(StringlibraryFileName)载入其文件由libraryFileName指定的动态库,必须指定其完全路径
staticvoidloadLibrary(StringlibraryName)载入其库名为libraryName的动态库
staticStringmapLibraryName(Stringlib)对应名为lib的库,返回一个指定平台的名字(在Java2中新增加的)
staticvoidrunFinalization()启动调用不用的但还不是回收站中的对象的finalize()方法。
staticvoidsetErr(PrintStreameStream)设置标准的错误(err)流为iStream
staticvoidsetIn(InputStreamiStream)设置标准的输入(in)流为oStream
staticvoidsetOut(PrintStreamoStream)设置标准的输出(out)流eStream
staticvoidsetProperties(PropertiessysProperties)设置由sysProperties指定的当前系统属性
StaticStringsetProperty(Stringwhich,Stringv)将v值赋给名为which的属性(在Java2中新增加的)
staticvoidsetSecurityManager(SecurityManagersecMan)设置由secMan指定的安全管理程序

  1. 5.1、使用currentTimeMillis()记录程序执行的时间


可以发现System类的一个特别有意义的用法是利用currentTimeMillis()方法来记录你的程序的不同部分的执行时间。currentTimeMillis()方法返回自从1970年1月1号午夜起到现在的时间,时间单位是毫秒。如果要记录你的程序中一段有问题程序的运行时间可以在这段程序开始之前存储当前时间,在该段程序结束之际再次调用currentTimeMillis()方法。执行该段程序所花费的时间为其结束时刻的时间值减去其开始时刻的时间值。下面的程序说明了这一点:
//Timingprogramexecution.

classElapsed{
publicstaticvoidmain(Stringargs[]){
longstart,end;

System.out.println("Timingaforloopfrom0to1,000,000");

//timeaforloopfrom0to1,000,000
start=System.currentTimeMillis();//getstartingtime
for(inti=0;i<1000000;i++);
end=System.currentTimeMillis();//getendingtime

System.out.println("Elapsedtime:"+(end-start));
}
}
这里是程序运行的一个输出样本(记住你的程序的运行结果可能与此不同):
Timingaforloopfrom0to1,000,000
Elapsedtime:10

  1. 5.2、使用arraycopy()


使用arraycopy()方法可以将一个任意类型的数组快速地从一个地方复制到另一个地方。这比使用Java中编写的循环要快的多。下面是一个用arraycopy()方法复制两个数组的例子。首先,将数组a复制给数组b,接下来,数组a中的所有元素向后移一位,然后数组b中元素向前移一位。
//Usingarraycopy().

classACDemo{
staticbytea[]={65,66,67,68,69,70,71,72,73,74};
staticbyteb[]={77,77,77,77,77,77,77,77,77,77};

publicstaticvoidmain(Stringargs[]){
System.out.println("a="+newString(a));
System.out.println("b="+newString(b));
System.arraycopy(a,0,b,0,a.length);
System.out.println("a="+newString(a));
System.out.println("b="+newString(b));
System.arraycopy(a,0,a,1,a.length-1);
System.arraycopy(b,1,b,0,b.length-1);
System.out.println("a="+newString(a));
System.out.println("b="+newString(b));
}
}
正如从下面的输出中看到的那样,可以使用相同的源和目的在任一方向进行复制:
a=ABCDEFGHIJ
b=MMMMMMMMMM
a=ABCDEFGHIJ
b=ABCDEFGHIJ
a=AABCDEFGHI
b=BCDEFGHIJJ

  1. 5.3、环境属性


下面的属性在Java2的所有环境中可以使用:
file.separatorjava.vendor.urlos.arch
java.class.pathjava.versionos.name
java.class.versionjava.vm.nameos.version
java.ext.dirsjava.vm.specification.namePath.separator
java.homejava.vm.specification.vendorUser.dir
java.specification.namejava.vm.specification.versionUser.home
java.specification.vendorjava.vm.vendorUser.name
java.specification.versionjava.vm.version
java.vendorline.separator
可以通过调用System.getProperty()方法来获得不同环境变量的值。例如下面的程序显示当前用户目录的路径:
classShowUserDir{
publicstaticvoidmain(Stringargs[]){
System.out.println(System.getProperty("user.dir"));
}
}

  1. 6、Object


正如我们在第1部分所提及的,Object类是其他所有类的一个超类。表14-12给出了Object类中定义的方法,这些方法对于每一个对象都是可用的。

表12由Object定义的方法
方法描述
Objectclone()ThrowsCloneNotSupportedException创建一个与调用对象一样的新对象
Booleanequals(Objectobject)如果调用对象等价于object返回true
voidfinalize()throwsThrowable默认的finalize()方法。常常被子类重载
finalClassgetClass()获得描述调用对象的Class对象
inthashCode()返回与调用对象关联的散列码
finalvoidnotify()恢复等待调用对象的线程的执行
finalvoidnotifyAll()恢复等待调用对象的所有线程的执行
StringtoString()返回描述对象的一个字符串
finalvoidwait()throwsInterruptedException等待另一个执行的线程
finalvoidwait(longmilliseconds)throwsInterruptedException等待直至指定毫秒数的另一个执行的线程
finalvoidwait(longmilliseconds,intnanoseconds)throwsInterruptedException等待直至指定毫秒加毫微秒数的另一个执行的线程

  1. 7、使用clone()和Cloneable接口


由Object类定义的绝大部分方法在本书其他部分讨论。而一个特别值得关注的方法是clone()。clone()方法创建调用它的对象的一个复制副本。只有那些实现Cloneable接口的类能被复制。
Cloneable接口没有定义成员。它通常用于指明被创建的一个允许对对象进行位复制(也就是对象副本)的类。如果试图用一个不支持Cloneable接口的类调用clone()方法,将引发一个CloneNotSupportedException异常。当一个副本被创建时,并没有调用被复制对象的构造函数。副本仅仅是原对象的一个简单精确的拷贝。
复制是一个具有潜在危险的操作,因为它可能引起不是你所期望的副作用。例如,假如被复制的对象包含了一个称为obRef的引用变量,当副本创建时,副本中的obRef如同原对象中的obRef一样引用相同的对象。如果副本改变了被obRef引用的对象的内容,那么对应的原对象也将被改变。这里是另一个例子。如果一个对象打开一个I/O流并被复制,两个对象将可操作相同的流。而且,如果其中一个对象关闭了流,而另一个对象仍试图对I/O流进行写操作的话,将导致错误。
由于复制可能引起问题,因此在Object内,clone()方法被说明为protected。这就意味着它必须或者被由实现Cloneable的类所定义的方法调用,或者必须被那些类显式重载以便它是公共的。让我们看关于下面每一种方法的例子。
下面的程序实现Cloneable接口并定义cloneTest()方法,该方法在Object中调用clone()方法:
//Demonstratetheclone()method.

classTestCloneimplementsCloneable{
inta;
doubleb;

//ThismethodcallsObject'sclone().
TestClonecloneTest(){
try{
//callcloneinObject.
return(TestClone)super.clone();
}catch(CloneNotSupportedExceptione){
System.out.println("Cloningnotallowed.");
returnthis;
}
}
}

classCloneDemo{
publicstaticvoidmain(Stringargs[]){
TestClonex1=newTestClone();
TestClonex2;

x1.a=10;
x1.b=20.98;

x2=x1.cloneTest();//clonex1

System.out.println("x1:"+x1.a+""+x1.b);
System.out.println("x2:"+x2.a+""+x2.b);
}
}
这里,方法cloneTest()在Object中调用clone()方法并且返回结果。注意由clone()方法返回的对象必须被强制转换成它的适当类型(TestClone)。
下面的例子重载clone()方法以便它能被其类外的程序所调用。为了完成这项功能,它的存取说明符必须是public,如下所示:
//Overridetheclone()method.

classTestCloneimplementsCloneable{
inta;
doubleb;

//clone()isnowoverriddenandispublic.
publicObjectclone(){
try{
//callcloneinObject.
returnsuper.clone();
}catch(CloneNotSupportedExceptione){
System.out.println("Cloningnotallowed.");
returnthis;
}
}
}

classCloneDemo2{
publicstaticvoidmain(Stringargs[]){
TestClonex1=newTestClone();
TestClonex2;

x1.a=10;
x1.b=20.98;

//here,clone()iscalleddirectly.
x2=(TestClone)x1.clone();

System.out.println("x1:"+x1.a+""+x1.b);
System.out.println("x2:"+x2.a+""+x2.b);
}
}
由复制带来的副作用最初一般是比较难发现的。通常很容易想到的是类在复制时是很安全的,而实际却不是这样。一般在没有一个必须的原因的情况下,对任何类都不应该执行Cloneable。

  1. 8、Class


Class封装对象或接口运行时的状态。当类被加载时,类型Class的对象被自动创建。不能显式说明一个类(Class)对象。一般地,通过调用由Object定义的getClass()方法来获得一个类(Class)对象。由Class定义的一些最常用的方法列在表14-13中。
表13由Class定义的一些方法
方法描述
staticClassforName(Stringname)throwsClassNotFoundException返回一个给定全名的Class对象
staticClassforName(Stringname,Booleanhow,ClassLoaderldr)throwsClassNotFoundException返回一个给定全名的Calss对象。对象由ldr指定的加载程序加载。如果how为true,对象被初始化,否则它将不被初始化(在Java2中新增加的)
Class[]getClasses()对每一个公共类和接口,返回一个类(Class)对象。这些公共类和接口是调用对象的成员
ClassLoadergetClassLoader()返回一个加载类或接口的ClassLoader对象,类或接口用于实例化调用对象
Constructor[]getConstructors()throwsSecurityException对这个类的所有的公共构造函数,返回一个Constructor对象
Constructor[]getDeclaredConstructors()throwsSecurityException对由这个类所声明的所有构造函数,返回一个Constructor对象
Field[]getDeclaredFields()throwsSecurityException对由这个类所声明的所有域,返回一个Field对象
Method[]getDeclaredMethods()throwsSecurityException对由这个类或接口所声明的所有方法,返回一个Method对象
Field[]getFields()throwsSecurityException对于这个类的所有公共域,返回一个Field对象
Class[]getInterfaces()当调用对象时,这个方法返回一个由该对象的类类型实现的接口数组。当调用接口时,这个方法返回一个由该接口扩展的接口数组
Method[]getMethods()throwsSecurityException对这个类中的所有公共方法,返回一个Method对象
StringgetName()返回调用对象的类或接口的全名
ProtectionDomaingetProtectionDomain()返回与调用对象有关的保护范围(在Java2中新增加的)
ClassgetSuperclass()返回调用对象的超类。如果调用对象是类型Object的,则返回值为空(null)
BooleanisInterface()如果调用对象是一个接口,则返回true。否则返回false
ObjectnewInstance()throwsIllegalAccessException,InstantiationException创建一个与调用对象类型相同的新的实例(即一个新对象)。这相当于对类的默认构造函数使用new。返回新对象
StringtoString()返回调用对象或接口的字符串表达式
由Class定义的方法经常用在需要知道对象的运行时类型信息的场合。如同表14-13中所说明的那样,由Class提供的方法确定关于特定的类的附加信息。例如它的公共构造函数,域以及方法。这对于本书后面将要讨论的JavaBeans函数是很重要的。
下面的程序说明了getClass()(从Object继承的)和getSuperclass()方法(从Class继承的):
//DemonstrateRun-TimeTypeInformation.
classX{
inta;
floatb;
}

classYextendsX{
doublec;
}

classRTTI{
publicstaticvoidmain(Stringargs[]){
Xx=newX();
Yy=newY();
ClassclObj;

clObj=x.getClass();//getClassreference
System.out.println("xisobjectoftype:"+
clObj.getName());

clObj=y.getClass();//getClassreference
System.out.println("yisobjectoftype:"+
clObj.getName());
clObj=clObj.getSuperclass();
System.out.println("y'ssuperclassis"+
clObj.getName());
}
}
这个程序的输出如下所示:
xisobjectoftype:X
yisobjectoftype:Y
y’ssuperclassisX

抽象类ClassLoader规定了类是如何加载的。应用程序可以创建扩展ClassLoader的子类,实现它的方法。这样做允许使用不同于通常由Java运行时系统加载的另一些方法来加载类。由ClassLoader定义的一些方法列在表14-14中。
表14由CalssLoader定义的一些方法
方法描述
finalClassdefineClass(Stringstr,byteb[],intindex,intnumBytes)throwsClassFormatError返回一个类(Class)对象,类的名字在str中,对象包含在由b指定的字节数组中。该数组中对象开始的位置下标由index指定,而该数组的长度为numBytes。b中的数据必须表示一个有效的对象
finalClassfindSystemClass(Stringname)throwsClassNotFoundException返回一个给定名字的类(Class)对象
abstractClassloadClass(Stringname,booleancallResolveClass)throwsClassNotFoundException如果callResolveClass为true,这个抽象方法的实现工具必须加载一个给定名字的类,并调用resolveClass()方法
finalvoidresolveClass(Classobj)用obj引用的类被解析(即,它的名字被输入在类名字空间中)

  1. 10、Math


Math类保留了所有用于几何学,三角学以及几种一般用途方法的浮点函数。Math定义了两个双精度(double)常数:E(近似为2.72)和PI(近似为3.14)。

  1. 10.1超越函数


下面的三种方法对一个以弧度为单位的角度接收一个双精度(double)参数并且返回它们各自的超越函数的结果:
方法描述
Staticdoublesin(doublearg)返回由以弧度为单位由arg指定的角度的正弦值
staticdoublecos(doublearg)返回由以弧度为单位由arg指定的角度的余弦值
staticdoubletan(doublearg)返回由以弧度为单位由arg指定的角度的正切值
下面的方法将超越函数的结果作为一个参数,按弧度返回产生这个结果的角度值。它们是其非弧度形式的反。
方法描述
staticdoubleasin(doublearg)返回一个角度,该角度的正弦值由arg指定
staticdoubleacos(doublearg)返回一个角度,该角度的余弦值由arg指定
staticdoubleatan(doublearg)返回一个角度,该角度的正切值由arg指定
staticdoubleatan2(doublex,doubley)返回一个角度,该角度的正切值为x/y

  1. 10.2指数函数

Math定义了下面的指数方法:
方法描述
staticdoubleexp(doublearg)返回arg的e
staticdoublelog(doublearg)返回arg的自然对数值
staticdoublepow(doubley,doublex)返回以y为底数,以x为指数的幂值;例如pow(2.0,3.0)返回8.0
staticdoublesqrt(doublearg)返回arg的平方根

  1. 10.3舍入函数

Math类定义了几个提供不同类型舍入运算的方法。这些方法列在表15中。

表15由Math定义的舍入方法
方法描述
staticintabs(intarg)返回arg的绝对值
staticlongabs(longarg)返回arg的绝对值
staticfloatabs(floatarg)返回arg的绝对值
staticdoubleabs(doublearg)返回arg的绝对值
staticdoubleceil(doublearg)返回大于或等于arg的最小整数
staticdoublefloor(doublearg)返回小于或等于arg的最大整数
staticintmax(intx,inty)返回x和y中的最大值
staticlongmax(longx,longy)返回x和y中的最大值
staticfloatmax(floatx,floaty)返回x和y中的最大值
staticdoublemax(doublex,doubley)返回x和y中的最大值
staticintmin(intx,inty)返回x和y中的最小值
staticlongmin(longx,longy)返回x和y中的最小值
staticfloatmin(floatx,floaty)返回x和y中的最小值
staticdoublemin(doublex,doubley)返回x和y中的最小值
staticdoublerint(doublearg)返回最接近arg的整数值
staticintround(floatarg)返回arg的只入不舍的最近的整型(int)值
staticlonground(doublearg)返回arg的只入不舍的最近的长整型(long)值

  1. 10.4其他的数学方法


除了给出的方法,Math还定义了下面这些方法:
staticdoubleIEEEremainder(doubledividend,doubledivisor)
staticdoublerandom()
staticdoubletoRadians(doubleangle)
staticdoubletoDegrees(doubleangle)
IEEEremainder()方法返回dividend/divisor的余数。random()方法返回一个伪随机数,其值介于0与1之间。在大多数情况下,当需要产生随机数时,通常用Random类。toRadians()方法将角度的度转换为弧度。而toDegrees()方法将弧度转换为度。这后两种方法是在Java2中新增加的。
下面是一个说明toRadians()和toDegrees()方法的例子:
//DemonstratetoDegrees()andtoRadians().
classAngles{
publicstaticvoidmain(Stringargs[]){
doubletheta=120.0;

System.out.println(theta+"degreesis"+
Math.toRadians(theta)+"radians.");

theta=1.312;
System.out.println(theta+"radiansis"+
Math.toDegrees(theta)+"degrees.");
}
}
程序输出如下所示:
120.0degreesis2.0943951023931953radians.
1.312radiansis75.17206272116401degrees.

  1. 11、StrictMath


在Java2的1.3版本中增加了StrictMath类。这个类定义一个与Math中的数学方法类似的一套完整的数学方法。两者的区别在于StrictMath中的方法对所有Java工具保证产生精确一致的结果,而Math中的方法更大程度上是为了提高性能。

  1. 12、Compiler


Compiler类支持创建将字节码编译而非解释成可执行码的Java环境。常规的程序不使用它。

  1. 13、Thread,ThreadGroup和Runnable


Runnable接口以及Thread和ThreadGroup类支持多线程编程。下面分别予以说明。
注意:关于管理线程,实现Runnable接口以及创建多线程程序的概述已在第11章中介绍过。

  1. 13.1Runnable接口

Runnable接口必须由启动执行的独立线程的类所实现。Runnable仅定义了一种抽象方法,叫做run()。该方法是线程的入口点。它的形式如下所示:
abstractvoidrun()
所创建的线程必须实现该方法。

  1. 13.2Thread


Thread创建一个新的执行线程。它定义了如下的构造函数:
Thread()
Thread(RunnablethreadOb)
Thread(RunnablethreadOb,StringthreadName)
Thread(StringthreadName)
Thread(ThreadGroupgroupOb,RunnablethreadOb)
Thread(ThreadGroupgroupOb,RunnablethreadOb,StringthreadName)
Thread(ThreadGroupgroupOb,StringthreadName)
threadOb是实现Runnable接口的类的一个实例,它定义了线程运行开始的地方。线程的名字由threadName指定。当名字未被指定时,Java虚拟机将创建一个。groupOb指定了新线程所属的线程组。当没有线程组被指定时,新线程与其父线程属于同一线程组。
下面的常数由Thread定义:
MAX_PRIORITY
MIN_PRIORITY
NORM_PRIORITY
正如所期望的那样,这些常数指定了最大,最小以及默认的线程优先权。
由Thread定义的方法列在表14-16中。在比Java2早的版本中,Thread中也包括了stop(),suspend()以及resume()方法。然而正如在第11章中解释的那样,这些方法由于其固有的不稳定性而在Java2中被摈弃了。在Java2中摈弃的还有countStackFrames()方法,因为它调用了suspend()方法。
表16由Thread定义的方法
方法描述
staticintactiveCount()返回线程所属的线程组中线程的个数
voidcheckAccess()引起安全管理程序检验当前的线程能访问和/或能改变在其上checkAccess()方法被调用的线程
staticThreadcurrentThread()返回一个Thread对象,该对象封装了调用这个方法的线程
voiddestroy()终止线程
staticintenumerate(Threadthreads[])将当前线程组中的所有Thread对象的拷贝放入threads中。返回线程的个数
ClassLoadergetContextClassLoader()返回用于对这个线程加载类和资源的类加载程序(在Java2中新增加的)
finalStringgetName()返回线程名
finalintgetPriority()返回线程的属性设置
finalThreadGroupgetThreadGroup()返回调用线程是其中一个成员的ThreadGroup对象
voidinterrupt()中断线程
staticbooleaninterrupted()如果当前执行的线程已经被预先设置了中断,则返回true;否则,返回false
finalbooleanisAlive()如果线程仍在运行中,则返回true;否则返回false
finalbooleanisDaemon()如果线程是一个后台进程线程(Java运行系统的一部分),则返回true;否则返回false
booleanisInterrupted()如果线程被中断,则返回true,否则返回false
finalvoidjoin()throwsInterruptedException等待直至线程终止
续表
方法描述
finalvoidjoin(longmilliseconds)throwsInterruptedException等待直到为终止线程而指定的以毫秒计时的时间
finalvoidjoin(longmilliseconds,intnanoseconds)throwsInterruptedException等待直到为终止线程而指定的以毫秒加毫微秒计时的时间
voidrun()开始线程的执行
voidsetContextClassLoader(ClassLoadercl)设置将被调用线程用于cl的类加载程序(在Java2中新增加的)
finalvoidsetDaemon(booleanstate)标记线程为后台进程线程
finalvoidsetName(StringthreadName)将线程的名字设置为由threadName指定的名字
finalvoidsetPriority(intpriority)设置由priority指定的线程优先权
staticvoidsleep(longmilliseconds)throwsInterruptedException以指定的毫秒为单位的时间长度挂起执行的线程
staticvoidsleep(longmilliseconds,intnanoseconds)throwsInterruptedException以指定的毫秒加毫微秒为单位的时间长度挂起执行的线程
voidstart()开始线程的执行
StringtoString()返回线程的等价字符串形式
staticvoidyield()调用线程将CPU让给其他的线程
14.13.3ThreadGroup
线程组(ThreadGroup)创建了一组线程。它定义了如下的两个构造函数:
ThreadGroup(StringgroupName)
ThreadGroup(ThreadGroupparentOb,StringgroupName)
对于两种形式,groupName指定了线程组的名字。第一种形式创建一个新的线程组,该线程组将当前的线程作为它的父线程。在第二种形式中,父线程由parentOb指定。
由ThreadGroup定义的方法列在表14-17中。在比Java2更早出现的Java版本中,ThreadGroup中也包括了stop(),suspend()以及resume()方法。这些方法由于其本身固有的不稳定性,而在Java2中被摈弃。
表14-17由ThreadGroup定义的方法
方法描述
intactiveCount()返回线程组加上以这个线程作为父类的所有线程组中线程的个数
intactiveGroupCount()返回调用线程是父类的线程的组数
finalvoidcheckAccess()引起安全管理程序检验调用线程能访问和/或能改变在其上checkAccess()方法被调用的线程组

finalvoiddestroy()撤消被调用的线程组(以及任一子线程组)
intenumerate(Threadgroup[])将构成调用线程组的线程放入group数组中
intenumerate(Threadgroup[],booleanall)将构成调用线程组的线程放入group数组中。如果all为true,那么线程组的所有子线程组中的线程也被放入group中
intenumerate(ThreadGroupgroup[])将调用线程组的子线程组放入group数组中
intenumerate(ThreadGroupgroup[],booleanall)将调用线程组的子线程组放入group数组中。如果all为true,所有子线程组的子线程组(等等)也被放入group中
finalintgetMaxPriority()返回对线程组设置的最大优先权
finalStringgetName()返回线程组名
finalThreadGroupgetParent()如果调用ThreadGroup对象没有父类,则返回null;否则返回调用对象的父类
finalvoidinterrupt()调用线程组中所有线程的interrupt()方法(在Java2中新增加的)
finalbooleanisDaemon()如果线程组是一个端口后台进程组,则返回true;否则返回false
booleanisDestroyed()如果线程组已经被破坏,则返回true;否则,返回false
voidlist()显示关于线程组的信息
finalbooleanparentOf(ThreadGroupgroup)如果调用线程是group的父线程(或group本身),则返回true;否则返回false
finalvoidsetDaemon(booleanisDaemon)如果isDaemon为true,那么调用线程组被标记为一个端口后台进程组
finalvoidsetMaxPriority(intpriority)对调用线程组设置最大优先权priority
StringtoString()返回线程组的字符串等价形式
voiduncaughtException(Threadthread,Throwablee)当一个异常未被捕获时,该方法被调用
线程组提供了一种方便的方法,可以将一组线程当做一个单元来管理。这在想挂起或恢复一些相关的线程的情况下,是特别有用的。例如假想在一个程序中,有一组线程被用来打印文档,另一组线程被用来将该文档显示在屏幕上,同时另一组线程将文档保存为磁盘文件。如果打印被异常中止了,想用一种很简单的方法停止所有与打印有关的线程。线程组为这种处理提供了方便。下面的程序说明了这种用法,在程序中创建两个线程组,每一线程组中有两个线程:
//Demonstratethreadgroups.
classNewThreadextendsThread{
booleansuspendFlag;

NewThread(Stringthreadname,ThreadGrouptgOb){
super(tgOb,threadname);
System.out.println("Newthread:"+this);
suspendFlag=false;
start();//Startthethread
}

//Thisistheentrypointforthread.
publicvoidrun(){
try{
for(inti=5;i>0;i--){
System.out.println(getName()+":"+i);
Thread.sleep(1000);
synchronized(this){
while(suspendFlag){
wait();
}
}
}
}catch(Exceptione){
System.out.println("Exceptionin"+getName());
}
System.out.println(getName()+"exiting.");
}

voidmysuspend(){
suspendFlag=true;
}

synchronizedvoidmyresume(){
suspendFlag=false;
notify();
}
}

classThreadGroupDemo{
publicstaticvoidmain(Stringargs[]){
ThreadGroupgroupA=newThreadGroup("GroupA");
ThreadGroupgroupB=newThreadGroup("GroupB");

NewThreadob1=newNewThread("One",groupA);
NewThreadob2=newNewThread("Two",groupA);
NewThreadob3=newNewThread("Three",groupB);
NewThreadob4=newNewThread("Four",groupB);

System.out.println("/nHereisoutputfromlist():");
groupA.list();
groupB.list();
System.out.println();

System.out.println("SuspendingGroupA");
Threadtga[]=newThread[groupA.activeCount()];
groupA.enumerate(tga);//getthreadsingroup
for(inti=0;i<tga.length;i++){
((NewThread)tga[i]).mysuspend();//suspendeachthread
}

try{
Thread.sleep(4000);
}catch(InterruptedExceptione){
System.out.println("Mainthreadinterrupted.");
}

System.out.println("ResumingGroupA");
for(inti=0;i<tga.length;i++){
((NewThread)tga[i]).myresume();//resumethreadsingroup
}

//waitforthreadstofinish
try{
System.out.println("Waitingforthreadstofinish.");
ob1.join();
ob2.join();
ob3.join();
ob4.join();
}catch(Exceptione){
System.out.println("ExceptioninMainthread");
}

System.out.println("Mainthreadexiting.");
}
}
该程序的一个输出样本如下所示:
Newthread:Thread[One,5,GroupA]
Newthread:Thread[Two,5,GroupA]
Newthread:Thread[Three,5,GroupB]
Newthread:Thread[Four,5,GroupB]
Hereisoutputfromlist():
java.lang.ThreadGroup[name=GroupA,maxpri=10]
Thread[One,5,GroupA]
Thread[Two,5,GroupA]
java.lang.ThreadGroup[name=GroupB,maxpri=10]
Thread[Three,5,GroupB]
Thread[Four,5,GroupB]
SuspendingGroupA
Three:5
Four:5
Three:4
Four:4
Three:3
Four:3
Three:2
Four:2
ResumingGroupA
Waitingforthreadstofinish.
One:5
Two:5
Three:1
Four:1
One:4
Two:4
Threeexiting.
Fourexiting.
One:3
Two:3
One:2
Two:2
One:1
Two:1
Oneexiting.
Twoexiting.
Mainthreadexiting.
注意在这个程序中,线程组A被挂起四秒。由于输出确认,造成线程One和线程Two暂停,但是线程Three和线程Four仍然运行。四秒钟之后,线程One和线程Two被恢复。注意线程组A是如何被挂起和恢复的。首先通过对线程组A调用enumerate()方法得到线程组A中的线程。然后每一个线程重复通过得到的数组而被挂起。为了恢复线程组A中的线程,序列再一次被遍历,每一个线程被恢复。最后一点:这个例子使用了Java2推荐使用的方法去完成挂起和恢复线程的任务。而没有用在Java2中被摈弃的方法suspend()和resume()。

  1. 14、ThreadLocal和InheritableThreadLocal

在Java2的java.lang中增加了两个与线程有关的类:
?ThreadLocal?用于创建线程局部变量。每个线程都拥有自己局部变量的拷贝。
?InheritableThreadLocal?创建可以被继承的线程局部变量。

  1. 15、Package


在Java2中增加了一个称为Package的类。这个类封装了与包有关的版本数据。包版本信息由于包的增值以及由于Java程序可能需要知道哪些包版本可以利用而变得更加重要。Package中定义的方法列在表14-18中。下面的程序通过显示程序当前已知的包而说明了Package。
表18由Package定义的方法
方法描述
StringgetImplementationTitle()返回调用包的标题
StringgetImplementationVendor()返回调用包的实现程序的程序名
StringgetImplementationVersion()返回调用包的版本号
StringgetName()返回调用包的名字
StaticPackagegetPackage(StringpkgName)返回一个由pkgName指定的Package对象
StaticPackage[]getPackages()返回调用程序当前已知的所有包
StringgetSpecificationTitle()返回调用包的规格说明的标题
StringgetSpecificationVendor()返回对调用包的规格说明的所有者的名字
StringgetSpecificationVersion()返回调用包的规格说明的版本号
InthashCode()返回调用包的散列码
BooleanisCompatibleWith(StringverNum)throwsNumberFormatException如果verNum小于或等于调用包的版本号,则返回true
BooleanisSealed()如果调用包被封,则返回true;否则返回false
BooleanisSealed(URLurl)如果调用包相对于url被封,则返回true;否则返回false。
StringtoString()返回调用包的等价字符串形式
//DemonstratePackage
classPkgTest{
publicstaticvoidmain(Stringargs[]){
Packagepkgs[];

pkgs=Package.getPackages();

for(inti=0;i<pkgs.length;i++)
System.out.println(
pkgs[i].getName()+""+
pkgs[i].getImplementationTitle()+""+
pkgs[i].getImplementationVendor()+""+
pkgs[i].getImplementationVersion()
);

}
}

在Java2的java.lang中也新增加了RuntimePermission。它与Java的安全机制有关,这里不做进一步的讨论。

  1. 17、Throwable


Throwable类支持Java的异常处理系统,它是派生所有异常类的类。在本书第10章已经讨论过它。


SecurityManager是一个子类可以实现的抽象类,它用于创建一个安全管理程序。一般不需要实现自己的安全管理程序,如果非要这样做,需要查阅与你的Java开发系统一起得到的相关文档。

  1. 19、Comparable接口


Java2在java.lang中新增加了一个接口:Comparable。实现Comparable的类的对象可以被排序。换句话说,实现Comparable的类包含了可以按某种有意义的方式进行比较的对象。Comparable接口说明了一个方法,该方法用于确定Java2调用一个类的实例的自然顺序。该方法如下所示:
intcompareTo(Objectobj)
这个方法比较调用对象和obj。如果他们相等,就返回0。如果调用对象比obj小,则返回一个负值。否则返回一个正值。
该接口由前面已经介绍的几种类实现。特别是Byte,Character,Double,Float,Long,Short,String以及Integer类定义了compareTo()方法。另外,下一章将会介绍到,实现这个接口的对象可以被使用在不同的集合中。

  1. 20、java.lang.ref和java.lang.reflect包


在Java中定义了两个java.lang的子包:java.lang.ref和java.lang.reflect。下面分别予以简单介绍。

  1. 20.1、java.lang.ref

在前面学到过,在Java中,垃圾回收工具自动确定何时对一个对象,没有引用存在。然后这个对象就被认为是不再需要的,同时它所占的内存也被释放。在Java2中新增加的java.lang.ref包中的类对垃圾回收处理提供更加灵活的控制。例如,假设你的程序创建了大量的在后面某个时间又想重新使用的对象,可以持续保持对这些对象的引用,但是这可能需要更多的内存开销。
作为替代,可以对这些对象定义“软”引用。如果可以利用的内存接近用完的话,一个可以“软实现”的对象可以从垃圾回收工具中释放。在那种情况下,垃圾回收工具将这个对象的“软”引用设为空(null)。否则,垃圾回收工具保存对象以便以后使用。
程序设计人员具有确定是否一个“软实现”的对象被释放的能力。如果它被释放了,可以重新创建它。如果没有释放,该对象对于后面的应用将一直是可以利用的。也可以为对象创建“弱”(weak)和“假想”(phantom)引用,不过关于这些以及java.lang.ref包中其他特性的讨论已经超过了本书的范围。

  1. 20.2、java.lang.reflect


Reflection是一个程序分析自己的能力。包java.lang.reflect提供了获得关于一个类的域、构造函数、方法和修改符的能力。需要这些信息去创建可以使你利用JavaBeans组件的软件工具。这个工具使用映射动态地确定组件的特征。这个主题将在第25章中讨论。
另外,包java.lang.reflect包括了一个可以动态创建和访问数组的类。

你可能感兴趣的:(java)