I'm regularly accused of pedantry. But I'm a programmer, so it's a virtue right? I mean I have to 'talk' to a machine, and the machine is 'dumb' and needs every last tiny little detail explicitly specified for it. So, in order to specify them, I must know these little details too and keep them in the front of my mind.
Today's rant was bought on at my general 'pissed-offed-ness' (see, I'm cool with poor language, I'm hip, I'm jiggy with it (for humans (sometimes))) with some of what I'm seeing in both Mono, and .NET. I checked out this nullable type library this morning too.
Let me point out what is pissing me off right now.
Microsoft defines System.Data.SqlTypes.SqlBoolean.Xor(SqlBoolean, SqlBoolean). According to the doco this “Performs a bitwise exclusive-OR operation on the supplied parameters.” and it returns a *SqlBoolean* with the result, according to the doco “The results of the logical XOR operation.” Note that they use the term 'logical XOR operation'. Then if you write the following code, which uses this library, you can see the various results, including the return of SqlBoolean.Null in some circumstances:
SqlBoolean a = new SqlBoolean(true);
SqlBoolean b = new SqlBoolean(false);
SqlBoolean c = SqlBoolean.Null;
MessageBox.Show(SqlBoolean.Xor(a, a).ToString()); // false
MessageBox.Show(SqlBoolean.Xor(a, b).ToString()); // true
MessageBox.Show(SqlBoolean.Xor(a, c).ToString()); // null
MessageBox.Show(SqlBoolean.Xor(b, b).ToString()); // false
MessageBox.Show(SqlBoolean.Xor(b, c).ToString()); // null
MessageBox.Show(SqlBoolean.Xor(c, c).ToString()); // null
So, now how is it that the 'logical XOR operation' could possibly return null? The answer is that it can't. Logic has no place for null. This is the realm of TVL (three valued logic). How could I possibly perform a 'bitwise' operation on a Null value? That's right, I can't. So, if this bitwise operator is to be defined, it must be undefined for Null values, and therefore should throw an exception if either input is null.
Mono picked up on this, and implemented their bitwise exclusive or like this:
return new SqlBoolean (x.Value ^ y.Value);
Notice that this uses the Value property, which is of type System.Boolean. If either type is Null then this operation will throw an exception. Correct! It actually implements the spec, whereas MS has not (IMNSHO).
The spec is lame however, because given the required semantics the output type is useless. Why return a SqlBoolean as the result of a function that can only return true or false? Yep, no good reason.
The nullable class library, has deprecated their Xor implementation, but they've kept the bogus (if deprecated) practice of returning Null if an input param is Null.
Mono has the best implementation, but the specified interface remains lame (and they didn't LAMESPEC it).
I'm going to finish writing my own library so I don't have to put up with these kinds of ludicrous inconsistencies! Call me a pedant if you like.. it's a few thousand lines of code, but they're just they way *I* like them.
Assert(myWay.Value ^ theirWay.Value);
John.
I didn't make my point well. The problem with 'exclusive or' which has the requirement of two values, by virtue of being able to 'exclude' the other, when you have three values you need to explicitly define what you mean, but no-one did.
The implicit definition (as per implementation) is that if anything is NULL the result is null otherwise the result is an exclusive or.
I give up.
John.