• 三元运算符(Ternary if-else operator)

   三元运算符,也称为条件运算符,有三个操作数,之所以称为运算符,是因为它确实会产生一个值。其格式如下:

boolean-exp ? value0 :value1

如果 boolean-exp 为true ,则取第一个值value0;如果 boolean-exp 为 false ,则取第二个值value1。该表达式可以用if-else 来简化,因此也称为 if-else 表达式。

:三元运算符最先起源于C,它使C语言更简练,另外一方面也提高了效率。但是,应该意识到,使用三元运算符降低了程序的可读性。

   三元运算符与if-else不同,因为它产生一个值。下面的例子是二者的比较。

  • 1-1 条件运算符与if-else的比较


//: operators/TernaryIfElse.java
import static net.mindview.util.Print.*;
public class TernaryIfElse {
  static int ternary(int i) {
    return i < 10 ? i * 100 : i * 10;
  }
  static int standardIfElse(int i) {
    if(i < 10)
      return i * 100;
    else
      return i * 10;
  }
  public static void main(String[] args) {
    print(ternary(9));
    print(ternary(10));
    print(standardIfElse(9));
    print(standardIfElse(10));
  }
}

程序运行的结果如下:

freemarker 模板三元运算符 三元运算符代码_大数据

说明

  1. 代码
import static net.mindview.util.Print.*;

已经在前面的文章中说明,可以参看[Thinking In Java]代码整理之移位操作符(shift operators)

  1. 三元运算符代码简短,if-else易于理解,所以应该深刻理解使用三元运算符的原因,它一般是给一个变量赋两个值中的一个时使用。
  • 强制类型转换(Casting operators)

   Java会在需要的时候将一种数据类型转换为另外一种合适的数据类型。比如,将一个integral类型的值赋给float point 型的变量时,Java编译器会自动地将int类型转化为float类型。

   具体的做法老外是这么说的:To perform a cast,put the desired data type inside parentheses to the left of any value.意思很清楚:Type value0 =(Type)value1。下面看一个例子。

  • 1-2 强制类型转换的例子
//: operators/Casting.java
public class Casting {
  public static void main(String[] args) {
    int i = 200;
    long lng = (long)i;
    lng = i; // "Widening," so cast not really required
    long lng2 = (long)200;
    lng2 = 200;
    // A "narrowing conversion":
    i = (int)lng2; // Cast required
  }
}

注意

  1. 在 C and C++ 中,类型换换会引起一些问题,在Java中,类型转换是安全的。但是应该注意到在缩小转换(narrowing conversion)—即将可以容纳更多数值的类型转换为容纳较少的信息的类型(比如int型转换为byte型)—时会出现丢失数据的问题,而此时,Java编译器会强制你使用数据类型转换,试图在告诉你:“This can be a dangerous thing to do—if you want me to do it anyway you must make the cast explicit(明确的).”。缩小转换的问题在扩大转化(widening conversion)是不存在的。
  2. Java允许将一种原始数据类型(在[Thinking In Java]代码整理之操作符(Operators)已给出)转换为另外一种原始数据类型(boolean类型除外,boolean类型不允许进行任何的数据类型转化)。类 类型是不允许转换的,要转变类的类型要用特定的方法,比如可以将子类转变为父类的类型,如可以将“橡树”转化为“树”,但不可以将其转化为“岩石”。
  • 截取与舍入(Truncation and rounding)

当执行缩小转换时就应该注意 截取与舍入 问题,例如将 浮点型(float)转化为 整型(integer)时,Java将会怎么做?比如:将29.7转化为int型时,是转化我29还是30?

下面的例子可以回答这个问题:

  • 1-3 截取与舍入的例子
//: operators/CastingNumbers.java
// What happens when you cast a float
// or double to an integral value?
import static net.mindview.util.Print.*;
public class CastingNumbers {
  public static void main(String[] args) {
    double above = 0.7, below = 0.4;
    float fabove = 0.7f, fbelow = 0.4f;
    print("(int)above: " + (int)above);
    print("(int)below: " + (int)below);
    print("(int)fabove: " + (int)fabove);
    print("(int)fbelow: " + (int)fbelow);
  }
}

程序运行的结果如下:

freemarker 模板三元运算符 三元运算符代码_大数据_02


说明

  1. 这里的int强制类型转换对小数进行取整,而不是四舍五入。
  2. 如果想得到四舍五入之后的结果,应该使用java.lang.Math中的round()方法。如下面代码
  • 1-4 四舍五入的例子
//: operators/RoundingNumbers.java
// Rounding floats and doubles.
import static net.mindview.util.Print.*;
public class RoundingNumbers {
  public static void main(String[] args) {
    double above = 0.7, below = 0.4;
    float fabove = 0.7f, fbelow = 0.4f;
    print("Math.round(above): " + Math.round(above));
    print("Math.round(below): " + Math.round(below));
    print("Math.round(fabove): " + Math.round(fabove));
    print("Math.round(fbelow): " + Math.round(fbelow));
  }
}

程序运行的结果如下:

freemarker 模板三元运算符 三元运算符代码_Java_03

  • 类型提升(Promotion)

   在char、byte、short的原始数据类型的移位操作中,操作之前会先将其类型提升为int型,当然结果就是int型,所以如果你想把int类型赋值给char、byte、short类型,就必须使用强制类型转换(由于将大数据类型转换为小的数据类型,就可能会丢书数据)。

   总之,一个表达式中最大的数据类型决定了结果的数据类型,例如,如将float型与double型相乘,结果是double;一个int型加一个long型,结果是long型。

  • Java has no "sizeof"

   在C++中有sizeof函数,用来取当前变量的内存长度,但Java中没有,因为Java中的变量长度都是很据类型来固定的。比如int为4字节,long为8字节。

:文章的代码摘自 Thinking in Java(Fourth Edition)英文版,作者 [美]Bruce Eckef,刘中兵 评注。


转载于:https://blog.51cto.com/020618/1210044