Null references (oh no, not again!)

Walter Bright newshound1 at digitalmars.com
Wed Mar 4 19:54:05 PST 2009


Ary Borenszweig wrote:
> Walter Bright escribió:
>> Ary Borenszweig wrote:
>>> Walter Bright escribió:
>>>> Ary Borenszweig wrote:
>>>>> It's not like that. They don't require you to initialize a variable 
>>>>> in it's initializer, but just before you read it for the fist time. 
>>>>> That's very different.
>>>>
>>>> The only way to do that 100% reliably is to instrument the running 
>>>> code.
>>>
>>> Java does it on compile time.
>>
>> Java is a severely constrained language. Even so, how does it do with 
>> this:
>>
>> Foo f;
>> if (x < 1) f = new Foo(1);
>> else if (x >= 1) f = new Foo(2);
>> f.member();
> 
> Whenever there are branches in code and a variable still doesn't have a 
> value at that point:
>  - if all branches assign a value to that variable, from now on the 
> variable has a value
>  - if not, at then end of the branches the variable still doesn't have a 
> value

That rule gets the wrong answer in the above case. Consider that in 
order to get where you want to go with this, the flow analysis has to 
always work, not most of the time work. Otherwise you get bug reports 
with phrases like "seems to", "sometimes", "somehow", "I can't figure it 
out", "I can't reproduce the problem", etc.

Here's another lovely case:

Foo f;
if (x < 1) f = new Foo();
... lots of code ...
if (x < 1) f.member();

The code is quite correct and bug-free, but flow analysis will tell you 
that f in f.member() is "possibly uninitialized".


>> ? (You might ask who would write such, but sometimes the conditions 
>> are much more complex, and/or are generated by generic code.)
>>
>>> If it's done only for local variables then you don't need to 
>>> instrument the running code.
>>
>> How about this:
>>
>> Foo f;
>> bar(&f);
>>
>> ? Or in another form:
>>
>> bar(ref Foo f);
>> Foo f;
>> bar(f);
>>
>> Java doesn't have ref parameters.
> 
> C# does have ref parameters and it also performs this kind of check.

It cannot do it and still support separate compilation.

> I just tried it and it says a parameter can't be passed by reference if it 
> doesn't have a value assigned.

I'll bet that they added this constraint when they got a bug report 
about that hole <g>.

> So your first example should be an error.
> 
> The same should be applied for &references.
> 
> (in your first example, if you want to pass f by reference so that bar 
> creates an instance of f, then it should be an out parameter).

Doesn't work if the function conditionally initializes it (that is not 
uncommon, consider the API case where if the function executes 
correctly, the reference arg is initialized and filled in with the results).

In other words, you have to start throwing in constraints like the C# 
copout or get rid of large chunks of the language like Java does.



More information about the Digitalmars-d mailing list