【问题标题】:Javascript one line If...else...else if statementJavascript 一行 If...else...else if 语句
【发布时间】:2015-05-16 13:53:16
【问题描述】:

我知道你可以通过var variable = (condition) ? (true block) : (else block) 使用一行 if/else 语句来设置变量,但我想知道是否有办法在其中放置一个 else if 语句。任何建议将不胜感激,谢谢大家!

【问题讨论】:

标签: javascript conditional-operator


【解决方案1】:

当然,您可以使用嵌套三元运算符,但它们很难阅读。

var variable = (condition) ? (true block) : ((condition2) ? (true block2) : (else block2))

【讨论】:

  • 是的,在这种情况下if() { ... } else if() { ... } else { ... } 可能更具可读性。
  • 任何三元运算符都难以阅读。它们很简洁,没有描述性。即使是非程序员也知道 if () else () 可能意味着什么。
【解决方案2】:

您可以根据需要链接任意数量的条件。如果你这样做:

var x = (false)?("1true"):((true)?"2true":"2false");

你会得到x="2true"

所以可以表示为:

var variable = (condition) ? (true block) : ((condition)?(true block):(false block))

【讨论】:

    【解决方案3】:

    这主要用于分配变量,它使用二项式条件,例如。

    var time = Date().getHours(); // or something
    
    var clockTime = time > 12 ? 'PM' : 'AM' ;
    

    没有ElseIf,为了开发不要使用链式,你可以使用switch,如果你在.js中有多个条件会更快

    【讨论】:

      【解决方案4】:

      tl;博士

      是的,你可以... 如果 a 则 a,否则如果 b,则如果 c 则 c(b),否则 b,否则为 null

      a ? a : (b ? (c ? c(b) : b) : null)
      
      a
        ? a
        : b
            ? c
              ? c(b)
              : b
            : null
      

      加长版

      用作内联 if-else 的三元运算符 ?:右结合。简而言之,这意味着最右边的 ? 首先得到馈送,它在左边恰好有 一个 最接近的操作数,而在右边有一个 :两个

      实际上,考虑以下语句(同上)

      a ? a : b ? c ? c(b) : b : null

      最右边的? 首先得到馈送,因此找到它及其周围的三个参数,然后连续向左扩展为另一个?

         a ? a : b ? c ? c(b) : b : null
                       ^                  <---- RTL
      1.            |1-?-2----:-3|
                   ^ <-
      2.        |1-?|--2---------|:-3---|
           ^ <-
      3.|1-?-2-:|--3--------------------|
      
      result: a ? a : (b ? (c ? c(b) : b) : null)
      

      这是计算机读取它的方式:

      1. 已读取术语 a
        节点:a
      2. 已读取非终结符 ?
        节点:a ?
      3. 已读取术语a
        节点:a ? a
      4. 已读取非终结符 :
        节点:a ? a :
      5. 已读取术语b
        节点:a ? a : b
      6. 读取非终结符?,触发右关联规则。关联性决定:
        节点:a ? a : (b ?
      7. 术语c 已读取。
        节点:a ? a : (b ? c
      8. 读取非终结符?,重新应用右关联规则。
        节点:a ? a : (b ? (c ?
      9. 已读取术语c(b)
        节点:a ? a : (b ? (c ? c(b)
      10. 已读取非终结符 :
        节点:a ? a : (b ? (c ? c(b) :
      11. 已读取术语 b
        节点:a ? a : (b ? (c ? c(b) : b
      12. 非终结符: 被读取。满足先前作用域的三元运算符?: 并关闭作用域。
        节点:a ? a : (b ? (c ? c(b) : b) :
      13. 已读取术语null
        节点:a ? a : (b ? (c ? c(b) : b) : null
      14. 没有要读取的令牌。关闭剩余的左括号。
        #结果是:a ? a : (b ? (c ? c(b) : b) : null)

      更好的可读性

      上面丑陋的单线可以(并且应该)为了可读性被重写为:
      (请注意,缩进确实隐式定义了正确的闭包就像括号 () 一样。)

      a
        ? a
        : b
            ? c
              ? c(b)
              : b
            : null
      

      例如

      return a + some_lengthy_variable_name > another_variable
              ? "yep"
              : "nop"
      

      更多阅读

      Mozilla: JavaScript Conditional Operator
      Wiki: Operator Associativity


      奖励:逻辑运算符

      var a = 0 // 1
      var b = 20
      var c = null // x=> {console.log('b is', x); return true} // return true here!
      
      a
        && a
        || b
            && c
              && c(b) // if this returns false, || b is processed
              || b
            || null
      

      在这个例子中使用逻辑运算符是丑陋和错误的,但这就是它们的亮点......

      “空合并”

      这种方法有一些细微的限制,如下面的链接所述。有关正确的解决方案,请参阅 Bonus2 中的 Nullish coalescing。

      function f(mayBeNullOrFalsy) {
        var cantBeNull = mayBeNullOrFalsy || 42                    // "default" value
        var alsoCantBe = mayBeNullOrFalsy ? mayBeNullOrFalsy : 42  // ugly...
        ..
      }
      

      短路评估

      false && (anything) // is short-circuit evaluated to false.
      true || (anything)  // is short-circuit evaluated to true.
      

      Logical operators
      Null coalescence
      Short-circuit evaluation


      Bonus2:JS 中的新功能

      适当的“空值合并”

      developer.mozilla.org~Nullish_coalescing_operator

      function f(mayBeNullOrUndefined, another) {
        var cantBeNullOrUndefined = mayBeNullOrUndefined ?? 42
        another ??= 37 // nullish coalescing self-assignment
        another = another ?? 37 // same effect
        ..
      }
      

      可选链接

      第四阶段完成提案https://github.com/tc39/proposal-optional-chaining https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Optional_chaining

      // before
      var street = user.address && user.address.street
      // after
      var street = user.address?.street
      
      // combined with Nullish coalescing
      // before
      var street = user.address
        ? user.address.street
        : "N/A"
      
      // after
      var street = user.address?.street ?? "N/A"
      
      // arrays
      obj.someArray?.[index]
      
      // functions
      obj.someMethod?.(args)
      

      【讨论】:

        【解决方案5】:

        我知道这是一个旧线程,但我想我会投入两分钱。三元运算符可以按以下方式嵌套:

        var variable = conditionA ? valueA : (conditionB ? valueB: (conditionC ? valueC : valueD));
        

        例子:

        var answer = value === 'foo' ? 1 :
            (value === 'bar' ? 2 : 
                (value === 'foobar' ? 3 : 0));
        

        【讨论】:

          【解决方案6】:

          简单来说:

          var x = (day == "yes") ? "Good Day!" : (day == "no") ? "Good Night!" : "";
          

          【讨论】:

          • 不,您的语法不正确,您的嵌套三元语句中缺少:。在浏览器中测试...
          • @Masood_Aslami 感谢您的更正。我投了赞成票。
          • @fyllepo 谢谢
          【解决方案7】:
            a === "a" ? do something
          : a === "b" ? do something
          : do something
          

          【讨论】:

          • 嗨,欢迎来到堆栈溢出。为了得到一个有用的答案,这个反应需要扩展。解释为什么这是问题的答案。
          【解决方案8】:

          如果-否则:

          a = b ? (true block) : (false block)
          

          if-else if-else:

          a = b ? (true block) : b = c ? (true block) : (false block)
          

          如果:

          a = b && (true block)
          

          if-else-if(嵌套):

          a = b ? (true block) : b = c && (true block)
          
          • 注意想那么多,直接实现看看结果,其中a、b、c是可变的

          【讨论】: