<div dir="ltr"><div class="gmail_quote"><div dir="ltr"><div>## Left-Associative Compound Conditional Statements<br></div><div>I would like the ability to compare many values in compound. As I do not see any real reason to avoid this, here is my proposal:</div><div><br></div><div>Following [this document](<a href="http://yehudakatz.com/2011/09/13/a-proposal-for-es-next-proposals/" target="_blank">http://yehudakatz.com/2011/09/13/a-proposal-for-es-next-proposals/</a>) (thanks @wykatz)</div><div><br></div><div>### What problem are we solving:</div><div>Often, it makes it easier and more convenient to compare values in a range as opposed to comparing one to another and that value to even another. In order to avoid this, JavaScript could add the ability to "chain" many comparators, failing after the first inequality that is falsy.</div><div><br></div><div>### Provide Non-Trivial Example Code Showing the Problem:</div><div>For the remainder of this issue/request, I will be using (almost exclusively) the "<" comparator, but any normal operators should work with this proposal, including but not limited to:</div><div>* ==</div><div>* ===</div><div>* ></div><div>* <</div><div>* >=</div><div>* <=</div><div>* yada yada yada (not an operator)</div><div><br></div><div>Two examples:</div><div>```javascript</div><div>let foo = 1, </div><div>    bar = 2,</div><div>    baz = 3;</div><div>if (foo < bar && bar < baz) {</div><div>    // ...do something!</div><div>}</div><div>```</div><div>While vaguely trivial, this snippet demonstrates the easiest way to accurately compare these three values in a basic conditional. We have to compare either the first two values and the second to values serially or in parallel.</div><div><br></div><div>Likewise (and slightly less trivial):</div><div>```javascript</div><div>let arr = [ 'foo', 'bar', 'baz' ];</div><div>for (var i = 0; i < arr.length; ++i) {</div><div>    // do something...</div><div>    if (i > 1) {</div><div>         break;</div><div>    }</div><div>}</div><div>```</div><div>The above illustrates an example where we want to iterate in a range. There are several solutions to this (including a compound condition in the `for` statement, cloning and slicing, or reversing the array and setting `i` greater than zero), but this is even less convenient than the original example!</div><div><br></div><div>### Show How the Example Code is Improved With the Proposal:</div><div>Now, we only have two left-associative conditions to evaluate as opposed to three</div><div>```javascript</div><div>let foo = 1, </div><div>    bar = 2,</div><div>    baz = 3;</div><div>if (foo < bar < baz) {</div><div>    // ...do something!</div><div>}</div><div>```</div><div><br></div><div>We have saved ourselves the trouble of including a good deal of logic in our simple `for` loop as well:</div><div>```javascript</div><div>let arr = [ 'foo', 'bar', 'baz' ];</div><div>for (let i = 0, y = 2; i < arr.length < y; ++i) {</div><div>    // do something...</div><div>}</div><div>```</div><div><br></div><div>What are Alternate ES3 (or ES5) Solutions to the Same Problem?: </div><div>I've included some solutions to how this can be avoided, it is worth noting in this section that this is not so much about this situation being unavoidable so much as it is a ~~matter of convenience~~.</div><div><br></div><div>Actually, scratch that, its not even JUST a matter of convenience. A simple evaluation in your developer console will tell you that this currently evaluates inconveniently (I am avoiding the term "incorrectly" here because it is not theoretically incorrect if we consider these evaluations left associative):</div><div>```javascript</div><div>1 < 2 < 3 // true where...</div><div>true < 3 // true...because</div><div>+true // 1</div><div>1 < 3 // true </div><div>```</div><div>Bear in mind that this is not a catch-all definition of this behavior:</div><div>```javascript</div><div>false === false == false // false (wut?)</div><div>```</div><div><br></div><div>### If the Proposal is For New Syntax, What if Anything Does it Desugar To?</div><div>The desugaring is shown above, but the concatenation of conditionals can be converted into their non-concatenated equivalents:</div><div>```javascript</div><div>(1 < 2 < 3) === (1< 2 & 2 < 3) // Not a typo</div><div>```</div><div><br></div><div>### If New Syntax, Can it Be Compiled to ES3 (or ES5)?</div><div>Absolutely, in the same way it has been outlined above</div><div><br></div><div>### Does the Proposal Change any Existing Semantics?</div><div>I'm not entirely sure this is semantic (because the comparators of any two values should evaluate in the same way they always have), but it is worth noting in this section that any two values should work with compound conditionals, not just numbers. For example, </div><div>```javascript</div><div>[] == [] === []</div><div>```</div><div>should fail comparison.</div><div><br></div><div>I realize this effectively makes `===` a silver bullet in compound conditional statements, but I can't see any other way this would work.</div><div><br></div><div>Please let me know if there is any more context or detail I can provide, or whether there are considerations I have not made.</div></div>
</div><br></div>