Есть два типа if
операторов в Java - классические: if {} else {}
и сокращенный: exp ? value1 : value2
. Один быстрее другого или они одинаковы?
заявление:
int x;
if (expression) {
x = 1;
} else {
x = 2;
}
тернарный оператор:
int x = (expression) ? 1 : 2;
if
используется в заявлениях.?
используется в выражениях.Ответы:
Здесь есть только один тип оператора «если». Другой - условное выражение. Что касается того, что будет работать лучше: они могут компилироваться в один и тот же байт-код, и я ожидал, что они будут вести себя идентично - или настолько близко, что вы определенно не захотите выбирать один из них с точки зрения производительности.
Иногда
if
оператор будет более читабельным, иногда условный оператор - более читабельным. В частности, я бы рекомендовал использовать условный оператор, когда два операнда просты и не имеют побочных эффектов, тогда как если основная цель двух ветвей - их побочные эффекты, я бы, вероятно, использовалif
оператор.Вот пример программы и байт-кода:
public class Test { public static void main(String[] args) { int x; if (args.length > 0) { x = 1; } else { x = 2; } } public static void main2(String[] args) { int x = (args.length > 0) ? 1 : 2; } }
Байт-код декомпилирован с помощью
javap -c Test
:public class Test extends java.lang.Object { public Test(); Code: 0: aload_0 1: invokespecial #1 4: return public static void main(java.lang.String[] Code: 0: aload_0 1: arraylength 2: ifle 10 5: iconst_1 6: istore_1 7: goto 12 10: iconst_2 11: istore_1 12: return public static void main2(java.lang.String[ Code: 0: aload_0 1: arraylength 2: ifle 9 5: iconst_1 6: goto 10 9: iconst_2 10: istore_1 11: return }
Как видите, есть небольшая разница в байт-коде - независимо от того,
istore_1
происходит ли это внутри марки или нет (в отличие от моей предыдущей очень ошибочной попытки :), но я был бы очень удивлен, если бы JITter закончился с другим собственным кодом.источник
main
и другое,main2
чтобы быть одинаковыми?Оба ваших примера, вероятно, будут компилироваться в идентичный или почти идентичный байт-код, поэтому разницы в производительности быть не должно.
Если бы была разница в скорости выполнения, вы все равно должны использовать наиболее идиоматическую версию (которая была бы второй для присвоения одной переменной на основе простого условия и двух простых подвыражений, а первая - для выполнения более сложных операций. или операции, которые не помещаются в одну строку).
источник
Это то же самое. Оба они довольно быстрые, обычно около 10-30 наносекунд. (в зависимости от модели использования) Важны ли для вас эти временные рамки?
Вы должны делать то, что считаете наиболее ясным.
источник
Просто добавьте ко всем другим ответам:
Второе выражение часто называют третичным / тернарным оператором / утверждением. Это может быть очень полезно, потому что возвращает выражение. Иногда это делает код более понятным для типичных коротких операторов.
источник
final
поля вы можете использовать блоки конструктора для установки значения (хотя условный оператор выглядит в миллиард раз лучше IMO), а с локальными переменными вы можете присвоить значение перед первым использованием позже в блоке кода, который вы Я думаю, единственный случай, когда тройка даст преимущество,if-else
- это вызовsuper(...)
илиthis(...)
внутри конструктора.ни то, ни другое - они будут скомпилированы так же.
источник
Тернарный оператор быстрее, чем условие if-else.
public class TerinaryTest { public static void main(String[] args) { int j = 2,i = 0; Date d1 = new Date(); for(long l=1;l<100000000;l++) if(i==1) j=1; else j=0; Date d2 = new Date(); for(long l=1;l<100000000;l++) j=i==1?1:0; Date d3 = new Date(); System.out.println("Time for if-else: " + (d2.getTime()-d1.getTime())); System.out.println("Time for ternary: " + (d3.getTime()-d2.getTime())); } }
Результаты теста:
Тропа-1:
Время для if-else: 63
Время для троичного: 31
Тропа-2:
Время для if-else: 78
Время для троичного: 47
Тропа-3:
Время для if-else: 94
Время для троичного: 31
Тропа-4:
Время для if-else: 78
Время для троичного: 47
источник