On the subject of error messages

Steven Schveighoffer via Digitalmars-d digitalmars-d at puremagic.com
Tue May 16 12:17:38 PDT 2017


On 5/16/17 2:29 PM, Stanislav Blinov wrote:
> On Tuesday, 16 May 2017 at 15:47:37 UTC, Steven Schveighoffer wrote:
>> On 5/16/17 9:54 AM, Stanislav Blinov wrote:
>>> On Tuesday, 16 May 2017 at 12:27:30 UTC, Steven Schveighoffer wrote:

>> When I have a type like this:
>>
>> struct S
>> {
>>    int foo;
>> }
>>
>> and the hand-written error message says: "Your type must be a struct
>> that contains an integer property named 'foo'". How does that help me
>> figure out what I did wrong? We can spend all day arguing over how
>> nice this message is, but the truth is, what the constraint writer put
>> in the constraints, and how the compiler is interpreting it, may be 2
>> different things. This helps nobody.
>
> It cannot be that way. Whoever wrote the constraint possesses knowledge
> about it's semantics. If they put wrong message there, then that's a
> bug, or they're a... well, not a very good person.

This is the only time I have issues. Most of the time, the constraint is 
straightforwardly simple and the problem is obvious just by looking at 
the constraint and the type.  When that's not the case, figuring out why 
the constraint doesn't seem to be doing what it says it's doing is the 
hard part.

This can be achieved any number of ways. The most straightforward and 
effective way is to have the compiler simply expose what it's doing.

>>> That is why (static) asserts have an optional string argument: to
>>> display a clean an readable error message, instead of just dumping some
>>> code on the user. The same thing, in my opinion, is needed for
>>> constraints.
>>
>> If assert(x == 5) would just print "Error: x == 4" automatically, we
>> could eliminate most needs for a message.
>
> You're taking overly simplified pieces of code and base your reasoning
> on them, while you know full well it's almost never this simple.
>
> assert(x.veryBadlyNamedFunction == obscureStateObtainedFromElsewhere);
>
> "Error: x.veryBadlyNamedFunction == 42"
>
> Very helpful message.

Not here to debate this "feature", but if it says what the return value 
was, and the name of the symbol it's checking against (and its value), 
then yes, combined with the usual stack trace it's incredibly useful. 
Most of the time, that's what I would normally write in the message, but 
that in itself isn't easy to do.

>> You could solve this with a message, but again, this is a huge task to
>> undertake on ALL code in existence, rather than fixing
>
> I seem to be expressing myself poorly, as I find I must repeat it the
> second time already: I never suggested to change any existing code. I
> suggested an *optional* mechanism of reporting errors.

No, I mean having the optional mechanism fixes nothing. Someone then has 
to go through all existing code and determine what the existing 
constraints are testing for, and then determine the best way to write 
the messages. That's not a trivial amount of work.

>> it all to a "good enough" degree that we don't need the messages. And
>> it avoids the "human compiler" that is prone to error.
>
> This again. No it does not. If there's a bug in the constraint, there is
> a bug in the constraint. Messages or no, it's all the same. Either it
> does what it's supposed to do, or it doesn't. Reporting the wrong
> message is a bug, as is returning false for compliant type, or true for
> malicious one.

There could be no bug in the constraint, but the message is misleading, 
wrong, or easy to misinterpret. It's adding another layer of potential 
issues.

-Steve


More information about the Digitalmars-d mailing list