现在的位置: 首页 > 综合 > 正文

JAVA2核心技术第1卷 笔记 01

2013年10月20日 ⁄ 综合 ⁄ 共 3831字 ⁄ 字号 评论关闭
  

关键字strictfp

自Java2以来,Java语言增加了一个关键字strictfp,虽然这个关键字在大多数场合比较少用,但是还是有必要了解一下。

strictfp的意思是FP-strict,也就是说精确浮点的意思。在Java虚拟机进行浮点运算时,如果没有指定strictfp关键字时,Java的编译器以及运行环境在对浮点运算的表达式是采取一种近似于我行我素的行为来完成这些操作,以致于得到的结果往往无法令你满意。而一旦使用了strictfp来声明一个类、接口或者方法时,那么所声明的范围内Java的编译器以及运行环境会完全依照浮点规范IEEE-754来执行。因此如果你想让你的浮点运算更加精确,而且不会因为不同的硬件平台所执行的结果不一致的话,那就请用关键字strictfp。

你可以将一个类、接口以及方法声明为strictfp,但是不允许对接口中的方法以及构造函数声明strictfp关键字,例如下面的代码:

1. 合法的使用关键字strictfp

strictfp interface A {}

public strictfp class FpDemo1 {
    strictfp void f() {}
}

2. 错误的使用方法

interface A {
    strictfp void f();
}

public class FpDemo2 {
    strictfp FpDemo2() {}
}

一旦使用了关键字strictfp来声明某个类、接口或者方法时,那么在这个关键字所声明的范围内所有浮点运算都是精确的,符合IEEE-754规范的。例如一个类被声明为strictfp,那么该类中所有的方法都是strictfp的

 

--------------------------------------------------------------------------------

const,goto

正确识别java语言的关键字(keyword)和保留字(reserved word)是十分重要的。Java的关键字对java的编译器有特殊的意义,他们用来表示一种数据类型,或者表示程序的结构等。保留字是为java预留的关键字,他们虽然现在没有作为关键字,但在以后的升级版本中有可能作为关键字。

  关键字列表

  abstract boolean break byte case
  catch char class continue default
  do double else extends false
  final finally float for if
  implements import instanceof int interface
  long native new null package
  private protected public return short
  static super switch synchronized this
  throw throws transient true try
  void volatile while
  
  保留字
  const,goto

  注意点

  识别java语言的关键字,不要和其他语言如c/c++的关键字混淆。

  const和goto是java的保留字。
  所有的关键字都是小写
  friendly,sizeof不是java的关键字

 

--------------------------------------------------------------------------------

关于检测一个数是否为NaN。不是使用

if (x == Double.NaN)

而是

if (Double.isNaN(x))

 

 

--------------------------------------------------------------------------------

StrictMath

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

在Math类里面的函数利用计算机浮点单元的例程来达到最快的性能。如果得到完全的可预测的结果,比最快的性能更重要的话,应该使用StrictMath方法。它从“自由分布数学库”(fdlibm)实现其运算法则,这样保证了在所有平台上都可以得到相同的结果。

 

 

--------------------------------------------------------------------------------

 

移位操作符:

无符号右移位操作符“>>>”在将bit串右移位时,从bit串的最左边填充0,这 和带符号右移位操作符“>>”不同。“>>”在将bit串右移位时,从bit串的最左边填充原来最左边的位。也就是说,bit串 原来最左边的位是符号位,如果为1,则在带符号右移时最左边始终填充1;如果为0,则在带符号右移时最左边始终填充0。
)?2{$r l ~)s `(T I3  移位操作符的例子见下表。

操作 结果 说明

00110010 << 2 11001000 右边始终填充0

结果一样
00110010 >> 2 00001100
00110010 >>> 2 00001100

结果不同
10110010 >> 2 11101100
10110010 >>> 2 00101100

 

 

 

--------------------------------------------------------------------------------

概念上讲,Java字符串就是Unicode字符序列。例如,字符串"Java/u2122"由5个Unicode字符J,a,v,a和™组成。Java没有内建的string类型。但是,标准Java库提供了一个类,很自然的,叫做String。每个被引起来的字符串就是一个String实例:

Java字符串是以char值序列的方式实现的。如我们在41页中提到的,char数据类型是一个表示UTF-16编码中各个Unicode代码点的代码单元。最常用的Unicode字符可以用一个单独的代码单元表示。增补字符需要一对代码单元。

length方法返回指定的UTF-16编码字符串所需代码单元的数量,例如:

String greeting = "Hello";

int n = greeting.length(); // is 5.

 

要得到真实的长度,即代码点的数量,调用:

int cpCount = greeting.codePointCount(0, greeting.length());

 
s.charAt(n) 返回位置n对应的代码单元,这里n介于0和s.length()-1之间。例如:

char first = greeting.charAt(0); // first is 'H'

char last = greeting.charAt(4); // last is 'o'

 

要获得第i个代码点,使用语句:

int index = greeting.offsetByCodePoints(0, i);

int cp = greeting.codePointAt(index);

在UTF-16编码中,增补字符需要两个代码单元,调用

char ch = sentence.charAt(i)  时如果碰到增补字符
并不返回一个空格,而是其第二个代码单元。要避免这个问题,你不应当使用char类型。这个类型太低级。

如果你的代码遍历一个字符串,并且你想逐个查看每个代码单元,请使用下面的语句:

int cp = sentence.codePointAt(i);

if (Character.isSupplementaryCodePoint(cp)) i += 2;

else i++;

幸运的是,codePointAt方法可以告诉我们何处是一个辅助字符的前一半或者后一半,并且对于任一一种都可以返回正确的结果。也就是说,你也可以用下面的语句进行回退操作

i--;

int cp = sentence.codePointAt(i);

if (Character.isSupplementaryCodePoint(cp)) i--;

 

offsetByCodePoints(int index, int codePointOffset)
          返回此 String 中从给定的 index 处偏移 codePointOffset 个代码点的索引。

codePointAt(int index)
          返回指定索引处的字符(Unicode 代码点)。

codePointCount(int beginIndex, int endIndex)
          返回此 String 的指定文本范围中的 Unicode 代码点数。

offsetByCodePoints(int index, int codePointOffset)
          返回此 String 中从给定的 index 处偏移 codePointOffset 个代码点的索引。

isSupplementaryCodePoint(int codePoint)
          确定指定字符(Unicode 代码点)是否在增补字符范围内。

 

 

--------------------------------------------------------------------------------

 

 
 

抱歉!评论已关闭.