digitalmars.D - Disallowing ?:?: syntax
- bearophile (11/11) Jan 05 2009 Where the operation isn't no symmetric, all binary operators (but assign...
-
Stewart Gordon
(8/13)
Jan 05 2009
- Miles (10/15) Jan 05 2009 The ternary operator is not ambiguous, I see no need for making it an
- Nick Sabalausky (44/59) Jan 05 2009 This makes my highly DRY-oriented mind think:
- Miles (7/12) Jan 05 2009 I think I have seen that using a mixture of recursive templates and lazy
- BCS (10/30) Jan 05 2009 I think not.
Where the operation isn't no symmetric, all binary operators (but assignment) in C are left-associative. But x?y:z is right-associative, so: x ? y : a ? b : c is: x ? y : (a ? b : c) My little proposal for D is to turn the following into a syntax error, to avoid possile programmer mistakes (so the programmer must put parentheses here to make it compile): x ? y : a ? b : c If it becomes a syntax error, then it's better if the error message tells to put how to fix generic code, for example: "x ? y : a ? b : c ==> x ? y : (a ? b : c)" Bye, bearophile
Jan 05 2009
bearophile wrote: <snip>My little proposal for D is to turn the following into a syntax error, to avoid possile programmer mistakes (so the programmer must put parentheses here to make it compile): x ? y : a ? b : c<snip> Here, right-associativity is intuitive - it's analogous to if-then-elseif. So it should probably still be allowed. IMO if there's anywhere where parentheses should be required, it's on the confusing combinations of bitwise and relational operators. Stewart.
Jan 05 2009
bearophile wrote:My little proposal for D is to turn the following into a syntax error, to avoid possile programmer mistakes (so the programmer must put parentheses here to make it compile): x ? y : a ? b : cThe ternary operator is not ambiguous, I see no need for making it an error. I have used such constructs very often, with no problem: writefln("Printer is %s.", status == OFFLINE ? "offline" : status == ONLINE ? "online" : status == CHECK ? "out of paper" : status == ONLINE_CHECK ? "on fire" : "unknown status"); That would become a real mess of parenthesis.
Jan 05 2009
"Miles" <_______ _______.____> wrote in message news:gjst46$2hh1$1 digitalmars.com...bearophile wrote:This makes my highly DRY-oriented mind think: While ?: is an expression-based counterpart to the statement-based if...else, maybe we could use a similar expression-based counterpart to switch? (I think I've seen such a thing in hardware description languages) -------------------- writefln("Printer is %s.", status ?? // Purely illustrative syntax OFFLINE => "offline" :: ONLINE => "online" :: CHECK => "out of paper" :: ONLINE_CHECK => "on fire" :: default => "unknown status"); -------------------- Although, I've often created re-usable lookup tables to handle that sort of thing: -------------------- char[] getPrinterStatusStr(uint code) { // Somthing like this, I forget the exact syntax and nuances. D's array literals are a PITA. char[][uint] printerStatusCodeToStr = [ OFFLINE : "offline", ONLINE : "online", CHECK : "out of paper", ONLINE_CHECK : "on fire", ]; return (code in printerStatusCodeToStr)? printerStatusCodeToStr[code] : "unknown status"; } writefln("Printer is %s.", getPrinterStatusStr(status)); -------------------- But the ??=>:: (again, purely illustrative syntax) would be a nice alternative to have at my disposal. And it would make writing getPrinterStatusStr much nicer. Back to the original ?:?: issue: If I were to ever chain ?:'s, Miles's example above is the only time I ever would feel comfortable omitting any disambiguating parens. If we got a ??=>:: (or something like it), then I would agree with making ?:?: illegal without disambiguating parens. But without a ??=>::, I think Miles's example provides a compelling reason to keep the ?:?:.My little proposal for D is to turn the following into a syntax error, to avoid possile programmer mistakes (so the programmer must put parentheses here to make it compile): x ? y : a ? b : cThe ternary operator is not ambiguous, I see no need for making it an error. I have used such constructs very often, with no problem: writefln("Printer is %s.", status == OFFLINE ? "offline" : status == ONLINE ? "online" : status == CHECK ? "out of paper" : status == ONLINE_CHECK ? "on fire" : "unknown status"); That would become a real mess of parenthesis.
Jan 05 2009
Nick Sabalausky wrote:This makes my highly DRY-oriented mind think: While ?: is an expression-based counterpart to the statement-based if...else, maybe we could use a similar expression-based counterpart to switch? (I think I've seen such a thing in hardware description languages)I think I have seen that using a mixture of recursive templates and lazy evaluation. But sure, that would be a nice addition to support a relatively common use-case. Two things I miss are the ?: GNU C extension ( a ?: b expands to a ? a (similar idea, but only tests for null reference).
Jan 05 2009
Reply to Miles,bearophile wrote:I think not. x ? y : a ? b : c => (x ? y : a) ? b : c or x ? y : a ? b : c => x ? y : (a ? b : c) without checking the actual syntax you can't tell which of the above will be used and (according to bearophile) if ?: followed after +/-/etc the first would be.My little proposal for D is to turn the following into a syntax error, to avoid possile programmer mistakes (so the programmer must put parentheses here to make it compile): x ? y : a ? b : cThe ternary operator is not ambiguous,I see no need for making it an error. I have used such constructs very often, with no problem:However I agree. Don't change it.writefln("Printer is %s.", status == OFFLINE ? "offline" : status == ONLINE ? "online" : status == CHECK ? "out of paper" :status == ONLINE_CHECK ? "on fire" :ha ha ha :)"unknown status"); That would become a real mess of parenthesis.
Jan 05 2009
BCS wrote:I think not. x ? y : a ? b : c => (x ? y : a) ? b : c or x ? y : a ? b : c => x ? y : (a ? b : c) without checking the actual syntax you can't tell which of the above will be used and (according to bearophile) if ?: followed after +/-/etc the first would be.It simply can't be the first, due to the kind of parser used for C and most of its derived languages (D included). When a '?' is found, the parser recurses until it finds a ':' (it gets stuck in a branch of the syntax tree until a colon token is found). This is in how the language is defined (http://www.digitalmars.com/d/2.0/expression.html): ConditionalExpression: OrOrExpression OrOrExpression ? Expression : ConditionalExpression So, the third operand to the ternary operator is a ConditionalExpression itself, the parser have no reason to finish this evaluation branch if it finds another '?', it naturally recurses. So, x ? y : a ? b : c => x ? y : (a ? b : c). But I think that I know what kind of ambiguity you are talking about now... For me, ambiguity is something like the <...> C++ template definition/instantiation operator, or the function declaration/object variable definition ambiguity.
Jan 05 2009
Reply to Miles,BCS wrote:You have just proven my exact point. To find how it parses you need to dig up the syntax, as you just did (Note I said that you can't tell how it's parsed *without* doing that). the other way: OrOrExpression: AndAndExpression OrOrExpression || AndAndExpressionI think not. x ? y : a ? b : c => (x ? y : a) ? b : c or x ? y : a ? b : c => x ? y : (a ? b : c) without checking the actual syntax you can't tell which of the above will be used and (according to bearophile) if ?: followed after +/-/etc the first would be.It simply can't be the first, due to the kind of parser used for C and most of its derived languages (D included). When a '?' is found, the parser recurses until it finds a ':' (it gets stuck in a branch of the syntax tree until a colon token is found). This is in how the language is defined (http://www.digitalmars.com/d/2.0/expression.html): ConditionalExpression: OrOrExpression OrOrExpression ? Expression : ConditionalExpression So, the third operand to the ternary operator is a ConditionalExpression itself, the parser have no reason to finish this evaluation branch if it finds another '?', it naturally recurses. So, x ? y : a ? b : c => x ? y : (a ? b : c).But I think that I know what kind of ambiguity you are talking about now... For me, ambiguity is something like the <...> C++ template definition/instantiation operator, or the function declaration/object variable definition ambiguity.Yes, I think you've spotted the point. I'm referring to ambiguities that will cause problems with <joke>I-BAL</joke> type parsers.
Jan 05 2009