Checking null value for a String/Object in java?

孤街醉人 提交于 2019-12-11 10:38:39

问题


What are the advantages of having

String a = null;
if(null != a)

over

if(a !=null)

I tried both statement and they worked fine. Any suggestions why should I go with the first one?


回答1:


Both are the same, however if you are checking for == on a boolean value:

if(a == true)

vs

if(true == a)

The latter would be better due to the tendency of typographical error by typing only = instead of ==:

if(a = true) //still compilable but not what you intended
if(true = a) //cannot be compiled, hence you know you typed it wrongly



回答2:


It just sounds more natural to put the item under question first.

In English you would say, "if answer is correct then check". You wouldn't say, "if correct is answer". People code the way they think and speak.

The only valid use case to switch the order (that I'm aware of) is where you're calling equals() but the object you're testing may be null. In such a case, it can be cleaner to do

if ("expected".equals(value))

than

if (value != null && value.equals("expected"))



回答3:


Advantage : Placing the constant value in the expression does not change the behavior of the program (unless the values evaluate to false). In programming languages that use a single equals sign (=) for assignment and not for comparison, a possible mistake is to assign a value unintentionally instead of writing a conditional statement.

Performance: No impact on performace

Readability: Its decreased

Cons The advantage of avoiding null behavior can also be considered a disadvantage, as null pointer errors can be hidden and only appear much later in the program.




回答4:


Well, nothing besides (the lack of) readability.

Also, it only works with boolean types:

boolean b = true;
if (b) {
    System.out.println("b, it is"); // << this
} else {
    System.out.println("not b");
}

Let's hack:

boolean b = false;
if (b = true) {
    System.out.println("b, it is"); // << this
} else {
    System.out.println("not b");
}

Other way around:

boolean b = true;
if (b = false) {
    System.out.println("b, it is");
} else {
    System.out.println("not b"); // << this
}

But with an int:

int a = 5;
if(a = 0) { // error: incompatible types: int cannot be converted to boolean
    System.out.println("0");
} else {
    System.out.println("not 0");
}

Same happens in your example, with a String and the a = null expression. So while this Yoda Comparison is useful in C, it is useless in Java.




回答5:


It seems like there is a tiny difference. Using JMH there seems tiny difference between in the SecureRandom test and random test. The difference is not significant in my opinion.

Benchmark                                                        Mode  Samples  Score  Score error   Units
c.g.v.YodaCompPerformace.countNullsArrayList                    thrpt      200  1.345        0.009  ops/ms
c.g.v.YodaCompPerformace.countNullsArrayListSecureRandom        thrpt      200  1.349        0.008  ops/ms
c.g.v.YodaCompPerformace.countNullsArrayListSecureRandomYoda    thrpt      200  1.358        0.009  ops/ms
c.g.v.YodaCompPerformace.countNullsArrayListYoda                thrpt      200  1.361        0.009  ops/ms

JHM code :

import java.security.SecureRandom;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Random;
import java.util.concurrent.TimeUnit;
import org.openjdk.jmh.annotations.Benchmark;
import org.openjdk.jmh.annotations.Level;
import org.openjdk.jmh.annotations.OutputTimeUnit;
import org.openjdk.jmh.annotations.Scope;
import org.openjdk.jmh.annotations.Setup;
import org.openjdk.jmh.annotations.State;

@OutputTimeUnit(TimeUnit.MILLISECONDS)
@State(Scope.Thread)
public class YodaCompPerformace {

    static List<Integer> arrayListSecureRandom;
    static List<Integer> arrayListRandom;

    @Setup(Level.Iteration)
    public void setUpSecureRandom() {
        arrayListSecureRandom = new ArrayList<>(100000);
        for (int count = 0; count < 100000; count++) {
            if ((count & 1) == 0) {
                arrayListSecureRandom.add(count);
            } else {
                arrayListSecureRandom.add(null);
            }
        }
        Collections.shuffle(arrayListSecureRandom, new SecureRandom());
    }

    @Setup(Level.Iteration)
    public void setUp() {
        arrayListRandom = new ArrayList<>(100000);
        for (int count = 0; count < 100000; count++) {
            if ((count & 1) == 0) {
                arrayListRandom.add(count);
            } else {
                arrayListRandom.add(null);
            }
        }
        Collections.shuffle(arrayListRandom, new Random());
    }
    @Benchmark
    public int countNullsArrayListSecureRandom() {
        int countNulls = 0;
        for (Integer i : arrayListSecureRandom) {
            if (i == null) {
                countNulls++;
            }
        }
        return countNulls;
    }
    @Benchmark
    public int countNullsArrayListSecureRandomYoda() {
        int countNulls = 0;
        for (Integer i : arrayListSecureRandom) {
            if (null == i) {
                countNulls++;
            }
        }
        return countNulls;
    }
    @Benchmark
    public int countNullsArrayList() {
        int countNulls = 0;
        for (Integer i : arrayListSecureRandom) {
            if (i == null) {
                countNulls++;
            }
        }
        return countNulls;
    }
    @Benchmark
    public int countNullsArrayListYoda() {
        int countNulls = 0;
        for (Integer i : arrayListSecureRandom) {
            if (null == i) {
                countNulls++;
            }
        }
        return countNulls;
    }

}


来源:https://stackoverflow.com/questions/35766437/checking-null-value-for-a-string-object-in-java

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!