NULL
is a hack
In C, the type “
int
” is for integers, and “
int*
” is for pointers to integers, right? Almost. A value of type “
int*
” is either a pointer to an integer
or a special value called “
null
”, which is slightly different. If you want to declare an variable that is just a pointer to an integer, you’re out of luck. The same goes for Java and C#. There is no type that means “reference to a string”. The
String
type means “either a reference to a string or a special value called
null
”.
Some languages differentiate between references and
optional references (i.e. a reference that might be
null
). C, Java, and C# only have the latter. I don’t know how
null
managed to sneak its way into every pointer type. This mess has been around for so long and had been so ingrained in my thinking that I never even noticed it until I was shown otherwise. Imagine if every
int
and
boolean
variable you used could optionally be
null
. Yeah, I know.
NullPointerException
is a basically a runtime type error. You thought you were dealing with a pointer to something, but you weren’t. If Java hadn’t muddied every reference type with
null
, the
NullPointerException
would never have existed. That’s
a million webpages that are crowding the internet for no good reason.
Languages
Haskell and ML (and statically typed functional languages in general) don’t let you stick
null
anywhere you want. There’s a generic type that adds optionality to an existing type. In Haskell, it’s just the extremely simple “
Maybe
” type; the type “
Maybe String
” is either a string or “
Nothing
”, but you can’t treat it like a string until you have checked.
The
Nice programming language is an example of a C/Java-like language that distinguishes between references and
optional references. If you want a reference to a string, the type is “
String
”. If you want something that is either a reference to a string or
null
, the type is “
?String
”. Unfortunately, due to the desire to interoperate well with Java, Nice’s implementation isn’t completely general. The wrinkles show in the treatment of tyep parameters and multiple levels of options (“
??String
”).
Some of Microsoft’s C#-derived research languages use C# annotations to say whether parameters and fields are
null
or not. The
relevant paper discusses the details. One of the more interesting complications arises because that the compiler can no longer just initialize a reference to
null
when it doesn’t have anything else to assign.