it-swarm.com.ru

Тернарный оператор быстрее, чем условие "если" в Java

Я склонен к " условно-условному синдрому ", что означает, что я склонен к использованию, если условия все время. Я редко использую троичный оператор. Например:

//I like to do this:
int a;
if (i == 0)
{
    a = 10;
}
else
{
    a = 5;
}

//When I could do this:
int a = (i == 0) ? 10:5;

Имеет ли значение, какой я использую? Что быстрее? Есть ли заметные различия в производительности? Лучше ли по возможности использовать самый короткий код?

106
JRunner

Имеет ли значение, какой я использую?

Да! Второе намного более читабельно. Вы торгуете одной линией, которая кратко выражает то, что вы хотите, против девяти линий эффективного беспорядка.

Что быстрее?

Ни.

Лучше ли по возможности использовать самый короткий код?

Не «когда это возможно», но, конечно, когда это возможно, без вредных последствий. Более короткий код является, по крайней мере, потенциально более читабельным, поскольку он фокусируется на соответствующей части, а не на побочных эффектах («шаблонный код»).

96
Konrad Rudolph

Если есть любая разница в производительности (в чем я сомневаюсь), она будет незначительной. Сконцентрируйтесь на написании самого простого и удобочитаемого кода, который вы можете.

Сказав это, попытайтесь преодолеть свое отвращение к условному оператору - хотя, безусловно, возможно злоупотреблять им, в некоторых случаях это может быть действительно полезным. В приведенном вами конкретном примере я бы определенно использовал условный оператор.

31
Jon Skeet

Пример троичного оператора:

int a = (i == 0) ? 10 : 5;

Вы не можете сделать назначение с if/else, как это: 

// invalid:
int a = if (i == 0) 10; else 5;

Это хорошая причина использовать троичный оператор. Если у вас нет назначения:

(i == 0) ? foo () : bar ();

if/else не так уж много кода: 

if (i == 0) foo (); else bar ();

В критических случаях производительности: измерьте это. Измерьте его с помощью целевой машины, целевой JVM с типичными данными, если есть узкое место. Остальное иди на удобочитаемость.

Краткая форма, встроенная в контекст, иногда очень удобна:

System.out.println ("Good morning " + (p.female ? "Miss " : "Mister ") + p.getName ()); 
26
user unknown

Да, это важно, но не из-за производительности выполнения кода.

Более быстрое (производительное) кодирование более актуально для циклического создания и создания объектов, чем простые синтаксические конструкции. Компилятор должен обрабатывать оптимизацию (все это будет примерно в одном бинарном файле!), Поэтому ваша цель должна заключаться в эффективности для You-From-The-Future (люди всегда являются узким местом в программном обеспечении).

Выступление Джоша Блоха "Беспокойство в исполнении" на Parleys.com

Ответ, цитирующий 9 строк против одной, может вводить в заблуждение: меньшее количество строк кода не всегда равно лучше . Тернарные операторы могут быть более кратким способом в ограниченных ситуациях (ваш пример хороший).

НО ими часто злоупотребляют, чтобы сделать код нечитаемым (что является кардинальным грехом) = не вкладывать троичных операторов!

Также учитывайте будущую ремонтопригодность, если намного проще расширить или изменить:

int a;
if ( i != 0 && k == 7 ){
    a = 10;
    logger.debug( "debug message here" );
}else
    a = 3;
    logger.debug( "other debug message here" );
}


int a = (i != 0 && k== 7 ) ? 10 : 3;  // density without logging nor ability to use breakpoints

постскриптум очень полный ответ stackoverflow в к троичному или не к троичному?

15
foupfeiffer

Тернарные операторы просто стенография. Они компилируются в эквивалентный оператор if-else, означающий, что они будут точно одинаковыми.

8
Jon Egeland

Кроме того, троичный оператор включает форму «необязательного» параметра. Java не допускает необязательные параметры в сигнатурах методов, но троичный оператор позволяет легко встроить выбор по умолчанию, если для значения параметра задано null.

Например:

public void myMethod(int par1, String optionalPar2) {

    String par2 = ((optionalPar2 == null) ? getDefaultString() : optionalPar2)
            .trim()
            .toUpperCase(getDefaultLocale());
}

В приведенном выше примере передача null в качестве значения параметра String возвращает строковое значение по умолчанию вместо NullPointerException. Это коротко и сладко и, я бы сказал, очень читабельно. Более того, как уже указывалось, на уровне байтового кода нет никакой разницы между троичным оператором и if-then-else. Как и в приведенном выше примере, решение о выборе полностью основано на удобочитаемости.

Более того, этот шаблон позволяет вам сделать параметр String действительно необязательным (если это считается полезным), перегружая метод следующим образом:

public void myMethod(int par1) {
    return myMethod(par1, null);
}
4
scottb

Для данного примера я предпочитаю троичный оператор или оператор условия (?) по определенной причине: я ясно вижу, что присвоение a не является обязательным. В простом примере несложно просканировать блок if-else, чтобы увидеть, что a назначен в каждом предложении, но представьте несколько назначений в каждом предложении:

if (i == 0)
{
    a = 10;
    b = 6;
    c = 3;
}
else
{
    a = 5;
    b = 4;
    d = 1;
}

a = (i == 0) ? 10 : 5;
b = (i == 0) ? 6  : 4;
c = (i == 0) ? 3  : 9;
d = (i == 0) ? 12 : 1;

Я предпочитаю последнее, чтобы вы знали, что не пропустили задание.

1
Matthew Carlson

Лучше всего использовать то, что читается лучше - во всем практическом эффекте разница в производительности.

В этом случае я думаю, что последнее утверждение читается лучше, чем первое выражение if, но старайтесь не злоупотреблять троичным оператором - иногда это может действительно сделать вещи намного менее понятными.

0
Michael Berry

Попробуйте использовать оператор switch case, но обычно это не узкое место в производительности.

0
Zava