Why does
if (x) {
f();
}
call f()
if x
is an empty string ""
?
Shouldn't empty strings in D implicitly convert to bool
false
like they do in Python and when empty arrays does it (in D)?
Update: I fixed the question. I had incorrectly reversed the reasoning logic. Luckily, the bright D minds understood what I meant anyway ;)
Conditions and if
statements and loops are cast to bool
by the compiler. So,
if(x) {...}
becomes
if(cast(bool)x) {...}
and in the case of arrays, casting to bool
is equivalent to testing whether its ptr
property is not null
. So, it becomes
if(x.ptr !is null) {...}
In the case of arrays, this is actually a really bad test, because null
arrays are considered to be the same as empty arrays. So, in most cases, you don't care whether an array is null
or not. An array is essentially a struct that looks like
struct Array(T)
{
T* ptr;
size_t length;
}
The ==
operator will check whether all of the elements referred to by ptr
are equal, but if length
is 0
for both arrays, it doesn't care what the value of ptr
is. That means that ""
and null
are equal (as are []
and null
). However, the is
operator explicitly checks the ptr
properties for equality, so ""
and null
won't be the same according to the is
operator, and whether a particular array which is empty has a null
ptr
depends on how its value was set. So, the fact that an array is empty really says nothing about whether it's null
or not. You have to check with the is
operator to know for sure.
The result of all this is that it's generally bad practice to put an array (or string) directly in a condition like you're doing with
if(x) {...}
Rather, you should be clear about what you're checking. Do you care whether it's empty? In that case, you should check either
if(x.empty) {...}
or
if(x.length == 0} {...}
Or do you really care that it's null
? In that case, use the is
operator:
if(x is null) {...}
The behavior of arrays in conditions is consistent with the rest of the language (e.g. pointer and reference types are checked to see whether they're null
or not), but unfortunately, in practice, such behavior for arrays is quite bug-prone. So, I'd advise that you just don't ever put an array by itself in the condition of an if
statement or loop.