【问题标题】:Testing whether a value is odd or even测试一个值是奇数还是偶数
【发布时间】:2011-09-06 21:13:54
【问题描述】:

我决定用一个非常简单的算法创建简单的 isEvenisOdd 函数:

function isEven(n) {
  n = Number(n);
  return n === 0 || !!(n && !(n%2));
}

function isOdd(n) {
  return isEven(Number(n) + 1);
}

如果 n 具有某些参数,那没关系,但在许多情况下都失败了。因此,我着手创建强大的函数,为尽可能多的场景提供正确的结果,以便只测试 javascript 数字范围内的整数,其他所有内容都返回 false(包括 + 和 - 无穷大)。请注意,零是偶数。

// Returns true if:
//
//    n is an integer that is evenly divisible by 2
//
// Zero (+/-0) is even
// Returns false if n is not an integer, not even or NaN
// Guard against empty string

(function (global) {

  function basicTests(n) {

    // Deal with empty string
    if (n === '') 
      return false;

    // Convert n to Number (may set to NaN)
    n = Number(n);

    // Deal with NaN
    if (isNaN(n)) 
      return false;

    // Deal with infinity - 
    if (n === Number.NEGATIVE_INFINITY || n === Number.POSITIVE_INFINITY)
      return false;

    // Return n as a number
    return n;
  }

  function isEven(n) {

    // Do basic tests
    if (basicTests(n) === false)
      return false;

    // Convert to Number and proceed
    n = Number(n);

    // Return true/false
    return n === 0 || !!(n && !(n%2));
  }
  global.isEven = isEven;

  // Returns true if n is an integer and (n+1) is even
  // Returns false if n is not an integer or (n+1) is not even
  // Empty string evaluates to zero so returns false (zero is even)
  function isOdd(n) {

    // Do basic tests
    if (basicTests(n) === false)
      return false;

    // Return true/false
    return n === 0 || !!(n && (n%2));
  }
  global.isOdd = isOdd;

}(this));

任何人都可以看到上述任何问题吗?是否有更好(即更准确、更快或更简洁而不会混淆)的版本?

有各种与其他语言相关的帖子,但我似乎找不到 ECMAScript 的最终版本。

【问题讨论】:

标签: javascript numbers


【解决方案1】:

使用模数:

function isEven(n) {
   return n % 2 == 0;
}

function isOdd(n) {
   return Math.abs(n % 2) == 1;
}

您可以检查 Javascript 中的任何值是否可以强制转换为数字:

Number.isFinite(parseFloat(n))

最好在isEvenisOdd 函数之外进行此检查,这样您就不必在这两个函数中重复错误处理。

【讨论】:

  • 0.1NaN 可以很好地使用上述功能。空数组有点痛苦,因为它等于 0...
  • @Alin - 我添加了一个数字检查。当您希望算术函数显式处理其他数据类型时,我不确定我是否理解这种情况,但如果这就是 OP 想要的......
  • return n == parseInt(n);改成return n === parseInt(n);怎么样?
  • 我想我在某处读到了在检查奇数时应该检查n % 2 !== 0 的内容,因为它不一定是 1,具体取决于语言。编辑:啊,这就是.abs 电话的用途。那没关系。
  • @Andy Ray - 你不能说 !isEven(number) for isOdd 因为这意味着 0.1 是奇数,因为它不是偶数。
【解决方案2】:

我更喜欢使用位测试:

if(i & 1)
{
    // ODD
}
else
{
    // EVEN
}

这测试第一个位是否表示奇数。

【讨论】:

  • 当然。对 base-2 数学使用模数应该是非法的 ;)
  • 三元:i & 1 == 1 ? console.log("odd") : console.log("even"); 此外,位级效率 +1(在 JS 中没有广泛使用)
  • @Jacksonkr 请注意,JavaScript 中没有“位级效率”,因为所有数字在 JavaScript 中都是浮点数,使用按位运算符意味着首先将其转换为 int,然后执行操作,然后再转换它返回一个浮点数。
  • @poke 正确它们是 Number 类型,但很高兴知道强类型语言有效率。
  • @AndrewCastellano 您正在测试单个位,而不是 i 的整个值。任何大于 0 的数字都是正确的,但这并不意味着它是奇数或偶数。查看:bitwisecmd.com 并根据输入的数字查看位数的扩展。
【解决方案3】:

下面的呢?我只在 IE 中对此进行了测试,但它非常乐意处理表示任意长度数字的字符串、整数或浮点数的实际数字,并且当传递布尔值、未定义、空值、数组或对象时,这两个函数都返回 false。 (在传入字符串时是否要忽略前​​导空格或尾随空格取决于您 - 我假设它们被 忽略并导致两个函数返回 false。)

function isEven(n) {
   return /^-?\d*[02468]$/.test(n);
}

function isOdd(n) {
   return /^-?\d*[13579]$/.test(n);
}

【讨论】:

  • 对于我的实现 isEven(2.122e3) 返回 true,但 isEven("2.122e3") 返回 false。相反,对于非常大的数字,我的 isEven() 失败,因为 JS 在将它们转换为正则表达式测试的字符串时将它们置于指数格式。哦,好吧。
  • @MartijnScheffer - 请随时将您必须购买的所有额外内存的账单寄给我。请注意,这个问题确实包括从其他类型到数字的转换,很明显,我在这里建议的重点是有一个简单的单行函数来处理数字 字符串。当然,根据我自己的评论,这实际上并不能处理所有可能的情况,但它仍然可能有用 - 正则表达式是验证用户输入数据的最简单方法,最初将是一个字符串。
  • 我在这里发表评论了吗?我没看到,但如果你想要一个我可以!,这不是一个正确的解决方案,这要慢数百倍,如果你想检查一个字符串是否有效,我们谈论的是数字而不是字符串数字和一个可以单独处理的整数。
  • @MartijnScheffer - 是的,你有一条评论,似乎在我回复后的某个时候被删除了。请注意,问题不仅与数字有关,OP 的代码还包括其他类型的转换。无论如何,感谢您的反馈。
【解决方案4】:

注意:也有负数。

function isOddInteger(n)
{
   return isInteger(n) && (n % 2 !== 0);
}

在哪里

function isInteger(n)
{
   return n === parseInt(n, 10);
}

【讨论】:

  • 这里 parseInt 不需要基数吗?
  • @blablabla 是的,并非所有实现都假定基数 = 10。
  • 很好地引用了负值。 Robert Brisita 的回答(后来添加)也涵盖了这一点。
【解决方案5】:

为什么不这样做:

    function oddOrEven(num){
        if(num % 2 == 0)
            return "even";
        return "odd";
    }
    oddOrEven(num);

【讨论】:

  • 甚至function isEven(num) { return num % 2 == 0 }
  • 或使用 ES6:const oddOrEven = num => num % 2 === 0 ? 'even' : 'odd'
【解决方案6】:

完成 Robert Brisita 的比特测试。

if ( ~i & 1 ) {
    // Even
}

【讨论】:

    【解决方案7】:
    var isOdd = x => Boolean(x % 2);
    var isEven = x => !isOdd(x);
    

    【讨论】:

      【解决方案8】:
      var isEven = function(number) {
          // Your code goes here!
          if (number % 2 == 0){
             return(true);
          }
          else{
             return(false);    
          }
      };
      

      【讨论】:

      • if ( <expression> ) return true else return false 范式可以总是简化为return ( <expression> )(因为if 中的表达式已经总是一个布尔值)。
      • 说return不是函数,就像说if不是函数,返回值时使用括号是完全有效的(即使它们在这里没有用处)跨度>
      【解决方案9】:

      史蒂夫梅恩答案的简单修改/改进!

      function isEvenOrOdd(n){
          if(n === parseFloat(n)){
              return isNumber(n) && (n % 2 == 0);
          }
          return false;
      }
      

      注意:如果无效则返回 false!

      【讨论】:

        【解决方案10】:

        我们只需要一行代码!

        这里有一种更新的替代方法,对 JS 函数使用新的 ES6 语法,对 if-else 语句调用使用 one-line syntax

        const isEven = num => ((num % 2) == 0) ? true : false;
        
        alert(isEven(8));  //true
        alert(isEven(9));  //false
        alert(isEven(-8)); //true
        

        【讨论】:

        • 短于let isEven = num => num % 2 === 0。 :-) 但实际上它与这里的许多其他答案没有什么不同。
        【解决方案11】:

        几个

        x % 2 == 0; // Check if even
        
        !(x & 1); // bitmask the value with 1 then invert.
        
        ((x >> 1) << 1) == x; // divide value by 2 then multiply again and check against original value
        
        ~x&1; // flip the bits and bitmask
        

        【讨论】:

          【解决方案12】:

          不同的方式:

          var isEven = function(number) {
            // Your code goes here!
            if (((number/2) - Math.floor(number/2)) === 0) {return true;} else {return false;};
          };
          
          isEven(69)
          

          【讨论】:

            【解决方案13】:

            其他方式使用字符串,因为为什么不

            function isEven(__num){
                return String(__num/2).indexOf('.') === -1;
            }
            

            【讨论】:

              【解决方案14】:
              if (testNum == 0);
              else if (testNum % 2  == 0);
              else if ((testNum % 2) != 0 );
              

              【讨论】:

              • 没有任何解释,您的贡献没有多大价值。它还重复了讨论中已经提出的信息。
              • 谢谢辛迪!只是提供一个解决方案!
              • 但是……这实际上并没有任何事情。它不应该返回一些东西吗?
              【解决方案15】:

              也许是这个? if(ourNumber % 2 !== 0)

              【讨论】:

              • 虽然这段代码 sn-p 可以解决问题,但including an explanation 确实有助于提高帖子的质量。请记住,您正在为将来的读者回答问题,而这些人可能不知道您的代码建议的原因。也请尽量不要用解释性的 cmets 挤满你的代码,这会降低代码和解释的可读性!
              【解决方案16】:
              var num = someNumber
                  isEven;
              parseInt(num/2) === num/2 ? isEven = true : isEven = false;
              

              【讨论】:

                【解决方案17】:

                for(var a=0; a<=20;a++){
                   if(a%2!==0){
                       console.log("Odd number "+a);
                   }
                }
                
                for(var b=0; b<=20;a++){
                    if(b%2===0){
                        console.log("Even number "+b);  
                    }     
                 }

                【讨论】:

                • 虽然此代码可能会解决问题,including an explanation 关于如何以及为什么解决问题将真正有助于提高您的帖子质量,并可能导致更多的赞成票。请记住,您正在为将来的读者回答问题,而不仅仅是现在提问的人。请edit您的回答添加解释并说明适用的限制和假设。
                【解决方案18】:

                要测试您是否有奇数或偶数,这也有效。

                const comapare = x => integer(checkNumber(x));
                
                function checkNumber (x) {
                   if (x % 2 == 0) {
                       return true;
                   } 
                   else if (x % 2 != 0) {
                       return false;
                    }
                }
                
                function integer (x) {
                   if (x) {
                       console.log('even');
                   } 
                   else {
                       console.log('odd');
                    }
                }
                

                【讨论】:

                  【解决方案19】:

                  使用现代 javascript 样式:

                  const NUMBERS = "nul one two three four five six seven ocho nueve".split(" ")
                  
                  const isOdd  = n=> NUMBERS[n % 10].indexOf("e")!=-1
                  const isEven = n=> isOdd(+n+1)
                  

                  【讨论】:

                  • isOdd('5')) 返回真。 isEven('5') 也返回 true。 isOdd(NaN) 引发错误。 :-(
                  • 固定isEven('5')isOdd(NaN) 可能会抛出错误。
                  • 脚本宿主不应该处理错误,函数应该。我总是被告知核心转储不是正常终止。 ;-)
                  【解决方案20】:

                  这个更简单!

                    var num = 3 //instead get your value here
                    var aa = ["Even", "Odd"];
                  
                    alert(aa[num % 2]);
                  

                  【讨论】:

                  • 这将返回未定义的num = -1
                  【解决方案21】:
                  function isEven(n) {return parseInt(n)%2===0?true:parseInt(n)===0?true:false}
                  

                  当0/甚至想要但是

                  isEven(0) //true
                  isEven(1) //false
                  isEven(2) //true
                  isEven(142856) //true
                  isEven(142856.142857)//true
                  isEven(142857.1457)//false
                  

                  【讨论】:

                  • return parseInt(n)%2===0?true:parseInt(n)===0。但是话又说回来,这与此处已经存在的许多其他答案相同。
                  • return parseInt(n)%2 === 0 || parseInt(n) === 0。但是为什么要parseInt?这对于像“32foo”和12.5这样的值返回true,它们不是偶数。
                  【解决方案22】:
                  if (i % 2) {
                  return odd numbers
                  }
                  
                  if (i % 2 - 1) {
                  return even numbers
                  }
                  

                  【讨论】:

                  • 任意数除以2的提示什么时候是2?
                  • 嗯,你说得对。我想念写 % 2 == 2。我的错。
                  猜你喜欢
                  • 1970-01-01
                  • 1970-01-01
                  • 2015-05-31
                  • 1970-01-01
                  • 2015-07-22
                  • 2015-03-03
                  • 2011-11-12
                  • 1970-01-01
                  • 1970-01-01
                  相关资源
                  最近更新 更多