В чем разница между double a = a + int b и int a + = double b?

Почему:

public class Addition { 
  public static void main() { 
    int a = 0; 
    double b = 1.0; 
    a = a + b;
    System.out.println(a); 
  }
}

не компилируется, но:

public class Addition { 
  public static void main() { 
    int a = 0; 
    double b = 1.0; 
    a += b; 
    System.out.println(a); 
  }
}

компилирует.

Ответ 1

В Java + = оператор имеет неявное преобразование в левый тип. Это относится ко всем составленным операторам.

Ответ 2

int = int + double по существу

int = double + double

и вы не можете сделать это без кастинга...

Параметр int + = double приводит результат к int, а другой требует кастинга.

Итак, a = (int) (a + b);

должен компилироваться.

Изменить: по запросу в комментариях... вот ссылка на большее чтение (не самая простая прочитанная, но самая правильная информация): http://docs.oracle.com/javase/specs/jls/se7/html/jls-15.html#jls-15.26.2

Ответ 3

double + int возвращает double, поэтому double = double + int является законным, см. JLS 5.1.2 Расширение примитивного преобразования с другой стороны int = double + int - "Сужение примитивного преобразования" и требует явного литья

Ответ 4

Как все уже заявили, + = имеет неявный литой. Чтобы проиллюстрировать это, я собираюсь использовать приложение, которое я написал некоторое время назад, которое идеально подходит для этих типов вопросов. Это онлайн-дизассемблер, чтобы вы могли проверить фактический байт-код, который создается: http://javabytes.herokuapp.com/

И таблица их значений: http://en.wikipedia.org/wiki/Java_bytecode_instruction_listings

Итак, давайте взглянем на байт-код из некоторого простого кода Java:

int i = 5;
long j = 8;
i += j;

Демонтированный код. Мои комментарии будут иметь//перед.

   Code:
        0: iconst_5  //load int 5 onto stack
        1: istore_0  //store int value into variable 0 (we called it i)
        2: ldc2_w #2; //long 8l
                     //load long 8 value onto stack.  Note the long 8l above
                     //is not my comment but how the disassembled code displays 
                     //the value long 8 being used with the ldc2_w instruction
        5: lstore_1  //store long value into variable 1 (we called it j)
        6: iload_0   //load int value from variable 0
        7: i2l       //convert int into a long.  At this point we have 5 long
        8: lload_1   //load value from variable 1
        9: ladd      //add the two values together.  We are adding two longs
                     //so it no problem
        10: l2i      //THIS IS THE MAGIC.  This converts the sum back to an int
       11: istore_0  //store in variable 0 (we called it i)