分享

java 常见错误

 jl_oracle 2011-11-14

操作符和赋值

使用操作符

赋值操作符
可以用常量或者表达式的结果来给基本变量赋值。使用了整数 (intshortbyte) 的表达式的结果至少为类型 int。不允许窄化转换,因为它们会导致精度损失。例如:

  byte b = 5;	
  byte c = 4;
  byte d = b + c;           // does not compile because int cannot fit in a byte

  float f = (float)35.67;   // implicitly double, so casting to float
  float f = 35.67F;

只能给布尔变量赋布尔类型的值。

如果我们将现有对象引用赋值给一个引用变量,那么两个引用变量就指向同一个对象。将子对象赋值给父对象是合法的,但是返之则不允许。如果一个对象实现了一个接口,那么您也可以将这个对象引用赋值给这个接口引用变量。例如:

  class Base{}
  public class Child extends Base
  {
    public static void main(String argv[])
    {
      Child child = new Child();
      Base base = new Base();
      base = child;     // Compiles fine
      child = base;     // Will not compile
    }
  }

instanceof 操作符
instanceof 操作符用于检查一个对象引用是否属于某种类型。这个类型可以是实例或者超类。例如:

  class A{}
  class B extends A 
  {
    public static void main(String args[])	
    {
      B b = new B();
      if(b instanceof A)
      System.out.println("b is of type A");  // "b is of type A" is printed
    }
  }

注意,如果一个对象的任何超类实现了特定的接口,那么这个对象就是这种接口类型。

加号 (+) 操作符
加号 (+) 操作符通常用于将两个数相加。如果操作数是 String 对象,那么加号 (+) 操作符就被覆盖以提供连接。例如:

  String s1 = "hello "; 
  String s2 = "World "; 
  System.out.println(s1 + s2); // prints "hello world"

如果一个操作数是 String ,而另一个不是,那么 Java 代码就会试图将另一个操作数转换为 String 表示。如果操作数是一个对象引用,那么就调用其 toString() 方法进行转换:

  int i = 10; 
  String s1 = " rivers"; 
  String s2 = i + s1; 
  System.out.printlns(s2);  // prints "10 rivers"

递增和递减操作符
两个快捷的算术操作符是将操作数加 1 的 ++ 和将操作数减 --

  • ++ 递增操作符 (值加 1)
  • -- 递减操作符 (值减 1)

这些操作符可以出现在操作数之前(前缀),也可以出现在操作数之后(后缀)。在前缀的情况下,在递增/递减操作之后对操作数的值进行计算。对于后缀的情况,在递增/递减操作之前对操作数的值进行计算,如下所示:

前缀(操作符放在操作数之前):

  int i = 10;
  int j = ++i;                  // j and i are 11
  System.out.println(--i);      // prints 10

后缀(操作符放在操作数之后):

  int i = 10;
  int j = i++;                  // j is 10, i becomes 11
  System.out.println(i--);      // prints 11

移位操作符
移位操作符向右或者向左移动数字的位,从而产生新的数字:

  • >> 右移(用原来符号位的内容填充左面的位)
  • << 左移(用零填充右边的位)
  • >>> 无符号右移(用零填充左边的位)

例如:

8 >> 1; 
Before shifting:	0000 0000 0000 0000 0000 0000 0000 1000
After shifting:		0000 0000 0000 0000 0000 0000 0000 0100

注意,移动后的位模式相当于十进制的 4。

位操作符
Java 提供了对其操作数进行位操作的四种操作符:

  • 如果两个操作数的位都是 1, & 操作符设置该位为 1。
  • 如果只有一个操作数的位是 1,则 ^ 操作符设置该位为 1。
  • 如果至少一个操作数的位为 1,则 | 操作符设置该位为 1。
  • ~ 操作符将操作数的每一位的值取反。

例如:

  class Test 
  {
    public static void main(String args[]) 
    {
      int x = 10 & 9;   // 1010 and 1001
      System.out.println(x);
    }  // prints 8, which is the decimal equivalent of 1000
  }

位操作符 &| 也可以用于布尔表达式。

逻辑操作符
四种逻辑操作符是 &&&|||

如果两个操作数都为 true,那么 &&& 操作符返回 true

如果至少有一个操作数为 true,那么 ||| 操作符返回 true

&| 操作符总是判断两个操作数。 &&|| 称为 short circuit 操作符,因为如果左边的操作数就可以确定布尔表达式的结果,那么它们就不对右边的操作数进行判断了。例如:

  if ((++x > 2) || (++y > 2)) { x++; }		
    //  y is incremented only if (++x > 2) is false

注意 ||&& 只能用于逻辑表达式。


equals() 方法

我们可以用 == 操作符来比较基本类型变量的值并确定它们是否相等。不过,如果用 == 操作符比较对象引用变量,那么如果引用变量指向同一个对象时它返回 ture。为了检查两个对象的相等性, Object 类提供了 equals(Object obj) 方法,可以覆盖它以对逻辑相等的对象返回 trueObject 类的 equals() 方法的默认实现只有当对象与它自己比较时才返回 true -- 也就是说,它的行为类似于 == 操作符。像 StringBoolean 这样的类覆盖了 equals() 方法,而 StringBuffer 则没有。例如:

  String s1 = "abc";
  String s2 = new String("abc");
  if (s1 == s2)      // returns false
    System.out.println("Same Object Reference");
  if (s1.equals(s2)) // returns true
    System.out.println("Equal Objects");    // prints "Equal Objects"


将变量传递给方法

如果传递的变量是基本类型,那么实际上只是变量的副本传递给了方法。所以在方法中修改变量不会影响实际的变量。

将对象变量传递给方法时,实际传递的是引用变量的副本。在这里,两个变量指向的是同一个对象。如果在方法里面修改对象,那么在原来的变量里也可以看到变化。尽管调用的方法可以改变由传递的变量引用的对象,但是它不能在改变调用方法中改变实际的变量。换句话说,不能对原始引用变量重新赋予其他的值。例如:

  class MyClass
  { 
    int a = 3; 
    void setNum(int a)
    { 
      this.a = a;
    }
    int getNum() 
    { 
      return a; 
    }
  }
  class Test
  {
    static void change(MyClass x) 
    {
      x.setNum(9);
    }
    public static void main(String args[])
    {
      MyClass my = new MyClass();
      change(my);
      System.out.println(my.getNum());	// Prints 9
    }
  }

在上面的例子中,可以看到改变 x 引用的对象也改变了由 my 引用的同一个对象。


小结

本节我们讨论了不同的操作符和赋值规则。您应该理解按位操作符 (&|) 和逻辑操作符 (& &||)的区别。要清楚用 == 操作符进行的是什么样的相等性比较,以及 equals() 方法对于对象的意义。同时,要记住对象是用引用值的副本传递的,而基本类型是用基本类型的值的副本传递的。


练习

问题:

编译和运行下面这段代码的结果是什么?

  Integer i= new Integer("10");
  if (i.toString() == i.toString())
    System.out.println("Equal");
  else
    System.out.println("Not Equal");

选项:

  • A. 编译错误
  • B. 输出“Equal”
  • C. 输出“Not Equal”
  • D. 以上都不是

正确答案:

  • C

说明:

toString() 方法返回等同于这个 String 对象的 String 。它每次调用时创建一个新的对象。 == 操作符比较两个对象引用的位模式而不是实际的 String 内容。因此比较返回 false,执行 else 语句,输出“Not Equal”。

    本站是提供个人知识管理的网络存储空间,所有内容均由用户发布,不代表本站观点。请注意甄别内容中的联系方式、诱导购买等信息,谨防诈骗。如发现有害或侵权内容,请点击一键举报。
    转藏 分享 献花(0

    0条评论

    发表

    请遵守用户 评论公约

    类似文章 更多