number - javascript validation message




JavaScript에서 10 진수 유효성 검사-IsNumeric() (20)

@CMS의 answer 내가 가진 문제는 NaN 과 Infinity를 제외하는 것입니다 NaN 과 Infinity는 많은 상황에서 유용한 숫자입니다. NaN 을 확인하는 한 가지 방법은 같지 않은 숫자 값을 확인하는 것입니다. NaN != NaN ! 실제로 처리하고 싶은 3 가지 테스트가 있습니다.

function isNumber(n) {
  n = parseFloat(n);
  return !isNaN(n) || n != n;
}
function isFiniteNumber(n) {
  n = parseFloat(n);
  return !isNaN(n) && isFinite(n);
}    
function isComparableNumber(n) {
  n = parseFloat(n);
  return (n >=0 || n < 0);
}

isFiniteNumber('NaN')
false
isFiniteNumber('OxFF')
true
isNumber('NaN')
true
isNumber(1/0-1/0)
true
isComparableNumber('NaN')
false
isComparableNumber('Infinity')
true

내 isComparableNumber는 또 다른 우아한 answer 과 거의 비슷하지만 16 진수 및 기타 숫자 문자열 표현을 처리합니다.

JavaScript에서 십진수의 유효성을 검사하는 가장 깨끗하고 효과적인 방법은 무엇입니까?

보너스 포인트 :

  1. 명쾌함. 솔루션은 깨끗하고 단순해야합니다.
  2. 크로스 플랫폼.

테스트 사례 :

01. IsNumeric('-1')      => true
02. IsNumeric('-1.5')    => true
03. IsNumeric('0')       => true
04. IsNumeric('0.42')    => true
05. IsNumeric('.42')     => true
06. IsNumeric('99,999')  => false
07. IsNumeric('0x89f')   => false
08. IsNumeric('#abcdef') => false
09. IsNumeric('1.2.3')   => false
10. IsNumeric('')        => false
11. IsNumeric('blah')    => false

RegExp없이 다음과 같이 할 수 있습니다.

function IsNumeric(data){
    return parseFloat(data)==data;
}

parseFloat 함수가 모든 작업을 수행 할 수 있다고 생각합니다. 아래 함수는 isNumeric(Infinity) == true 포함 isNumeric(Infinity) == true 페이지의 모든 테스트를 통과 isNumeric(Infinity) == true .

function isNumeric(n) {

    return parseFloat(n) == n;
}

나에게 이것은 가장 좋은 방법입니다.

isNumber : function(v){
   return typeof v === 'number' && isFinite(v);
}

다음을 추가하고 싶습니다.

1. IsNumeric('0x89f') => true
2. IsNumeric('075') => true

양의 16 진수는 0x 시작하고 음의 16 진수는 -0x 시작합니다. 양의 oct 숫자는 0 시작하고 음의 oct 숫자는 -0 시작합니다. 이것은 이미 언급 된 대부분의 것을 취하지 만 16 진수와 8 진수, 음의 과학, 무한대를 포함하고 십진 과학을 제거했습니다 ( 4e3.2 는 유효하지 않습니다).

function IsNumeric(input){
  var RE = /^-?(0|INF|(0[1-7][0-7]*)|(0x[0-9a-fA-F]+)|((0|[1-9][0-9]*|(?=[\.,]))([\.,][0-9]+)?([eE]-?\d+)?))$/;
  return (RE.test(input));
}

받아 들여진 대답은 시험 # 7에 실패했으며 마음이 바뀌었기 때문입니다. 그래서 이것은 내가 받아 들인 대답에 대한 답변입니다.

일부 프로젝트 중에 일부 데이터의 유효성을 검사하고 가능한 한 수학 연산에 사용할 수있는 자바 스크립트 숫자 값인지 확인해야했습니다.

jQuery 및 일부 다른 Javascript 라이브러리에는 일반적으로 isNumeric 이라는 이러한 함수가 이미 포함되어 있습니다. 스택 오버 플로우 에 대한 게시물 도 앞에서 언급 한 라이브러리가 사용하는 것과 동일한 일반적인 루틴으로 대답으로 널리 받아 들여졌습니다.

function isNumber(n) {
  return !isNaN(parseFloat(n)) && isFinite(n);
}

첫째, 인수가 길이 1의 배열이고 단일 요소가 위의 논리에 의해 숫자로 간주되는 유형 인 경우 위의 코드는 true를 리턴합니다. 제 생각에는 배열이면 숫자가 아닙니다.

이 문제를 완화하기 위해 논리에서 어레이를 할인하는 검사를 추가했습니다.

function isNumber(n) {
  return Object.prototype.toString.call(n) !== '[object Array]' &&!isNaN(parseFloat(n)) && isFinite(n);
}

물론 Object.prototype.toString.call(n) !== '[object Array]' 대신 Array.isArray , jquery $.isArray 또는 프로토 타입 Object.isArray 를 사용할 수도 있습니다 Object.prototype.toString.call(n) !== '[object Array]'

두 번째 문제는 음의 16 진 정수 리터럴 문자열 ( "-0xA"-> -10)이 숫자로 계산되지 않았다는 것입니다. 그러나 양의 16 진 정수 리터럴 문자열 ( "0xA"-> 10)은 숫자로 처리되었습니다. 둘 다 유효한 숫자 여야했습니다.

그런 다음 이것을 고려하여 논리를 수정했습니다.

function isNumber(n) {
  return Object.prototype.toString.call(n) !== '[object Array]' &&!isNaN(parseFloat(n)) && isFinite(n.toString().replace(/^-/, ''));
}

함수가 호출 될 때마다 정규 표현식 생성이 걱정되면 클로저 내에서 다시 작성할 수 있습니다.

var isNumber = (function () {
  var rx = /^-/;

  return function (n) {
      return Object.prototype.toString.call(n) !== '[object Array]' &&!isNaN(parseFloat(n)) && isFinite(n.toString().replace(rx, ''));
  };
}());

그런 다음 CMSs +30 테스트 사례 를 가져 와서 jsfiddle 에서 테스트를 복제하여 추가 테스트 사례와 위에서 설명한 솔루션을 추가했습니다.

널리 사용되는 답변을 대체하지는 않지만 isNumeric 함수의 결과로 기대하는 것 이상이라면 도움이 될 것입니다.

편집 : Bergi 지적한 것처럼 숫자로 간주 될 수있는 다른 가능한 개체가 있으며 블랙리스트보다 화이트리스트에 Bergi 것이 좋습니다. 이를 염두에두고 기준에 추가하겠습니다.

내 isNumeric 함수가 숫자 또는 문자열 만 고려하기를 원합니다.

이를 염두에두고 사용하는 것이 좋습니다

function isNumber(n) {
  return (Object.prototype.toString.call(n) === '[object Number]' || Object.prototype.toString.call(n) === '[object String]') &&!isNaN(parseFloat(n)) && isFinite(n.toString().replace(/^-/, ''));
}

솔루션 테스트

var testHelper = function() {

  var testSuite = function() {
    test("Integer Literals", function() {
      ok(isNumber("-10"), "Negative integer string");
      ok(isNumber("0"), "Zero string");
      ok(isNumber("5"), "Positive integer string");
      ok(isNumber(-16), "Negative integer number");
      ok(isNumber(0), "Zero integer number");
      ok(isNumber(32), "Positive integer number");
      ok(isNumber("040"), "Octal integer literal string");
      ok(isNumber(0144), "Octal integer literal");
      ok(isNumber("-040"), "Negative Octal integer literal string");
      ok(isNumber(-0144), "Negative Octal integer literal");
      ok(isNumber("0xFF"), "Hexadecimal integer literal string");
      ok(isNumber(0xFFF), "Hexadecimal integer literal");
      ok(isNumber("-0xFF"), "Negative Hexadecimal integer literal string");
      ok(isNumber(-0xFFF), "Negative Hexadecimal integer literal");
    });

    test("Foating-Point Literals", function() {
      ok(isNumber("-1.6"), "Negative floating point string");
      ok(isNumber("4.536"), "Positive floating point string");
      ok(isNumber(-2.6), "Negative floating point number");
      ok(isNumber(3.1415), "Positive floating point number");
      ok(isNumber(8e5), "Exponential notation");
      ok(isNumber("123e-2"), "Exponential notation string");
    });

    test("Non-Numeric values", function() {
      equals(isNumber(""), false, "Empty string");
      equals(isNumber("        "), false, "Whitespace characters string");
      equals(isNumber("\t\t"), false, "Tab characters string");
      equals(isNumber("abcdefghijklm1234567890"), false, "Alphanumeric character string");
      equals(isNumber("xabcdefx"), false, "Non-numeric character string");
      equals(isNumber(true), false, "Boolean true literal");
      equals(isNumber(false), false, "Boolean false literal");
      equals(isNumber("bcfed5.2"), false, "Number with preceding non-numeric characters");
      equals(isNumber("7.2acdgs"), false, "Number with trailling non-numeric characters");
      equals(isNumber(undefined), false, "Undefined value");
      equals(isNumber(null), false, "Null value");
      equals(isNumber(NaN), false, "NaN value");
      equals(isNumber(Infinity), false, "Infinity primitive");
      equals(isNumber(Number.POSITIVE_INFINITY), false, "Positive Infinity");
      equals(isNumber(Number.NEGATIVE_INFINITY), false, "Negative Infinity");
      equals(isNumber(new Date(2009, 1, 1)), false, "Date object");
      equals(isNumber(new Object()), false, "Empty object");
      equals(isNumber(function() {}), false, "Instance of a function");
      equals(isNumber([]), false, "Empty Array");
      equals(isNumber(["-10"]), false, "Array Negative integer string");
      equals(isNumber(["0"]), false, "Array Zero string");
      equals(isNumber(["5"]), false, "Array Positive integer string");
      equals(isNumber([-16]), false, "Array Negative integer number");
      equals(isNumber([0]), false, "Array Zero integer number");
      equals(isNumber([32]), false, "Array Positive integer number");
      equals(isNumber(["040"]), false, "Array Octal integer literal string");
      equals(isNumber([0144]), false, "Array Octal integer literal");
      equals(isNumber(["-040"]), false, "Array Negative Octal integer literal string");
      equals(isNumber([-0144]), false, "Array Negative Octal integer literal");
      equals(isNumber(["0xFF"]), false, "Array Hexadecimal integer literal string");
      equals(isNumber([0xFFF]), false, "Array Hexadecimal integer literal");
      equals(isNumber(["-0xFF"]), false, "Array Negative Hexadecimal integer literal string");
      equals(isNumber([-0xFFF]), false, "Array Negative Hexadecimal integer literal");
      equals(isNumber([1, 2]), false, "Array with more than 1 Positive interger number");
      equals(isNumber([-1, -2]), false, "Array with more than 1 Negative interger number");
    });
  }

  var functionsToTest = [

    function(n) {
      return !isNaN(parseFloat(n)) && isFinite(n);
    },

    function(n) {
      return !isNaN(n) && !isNaN(parseFloat(n));
    },

    function(n) {
      return !isNaN((n));
    },

    function(n) {
      return !isNaN(parseFloat(n));
    },

    function(n) {
      return typeof(n) != "boolean" && !isNaN(n);
    },

    function(n) {
      return parseFloat(n) === Number(n);
    },

    function(n) {
      return parseInt(n) === Number(n);
    },

    function(n) {
      return !isNaN(Number(String(n)));
    },

    function(n) {
      return !isNaN(+('' + n));
    },

    function(n) {
      return (+n) == n;
    },

    function(n) {
      return n && /^-?\d+(\.\d+)?$/.test(n + '');
    },

    function(n) {
      return isFinite(Number(String(n)));
    },

    function(n) {
      return isFinite(String(n));
    },

    function(n) {
      return !isNaN(n) && !isNaN(parseFloat(n)) && isFinite(n);
    },

    function(n) {
      return parseFloat(n) == n;
    },

    function(n) {
      return (n - 0) == n && n.length > 0;
    },

    function(n) {
      return typeof n === 'number' && isFinite(n);
    },

    function(n) {
      return !Array.isArray(n) && !isNaN(parseFloat(n)) && isFinite(n.toString().replace(/^-/, ''));
    }

  ];


  // Examines the functionsToTest array, extracts the return statement of each function
  // and fills the toTest select element.
  var fillToTestSelect = function() {
    for (var i = 0; i < functionsToTest.length; i++) {
      var f = functionsToTest[i].toString();
      var option = /[\s\S]*return ([\s\S]*);/.exec(f)[1];
      $("#toTest").append('<option value="' + i + '">' + (i + 1) + '. ' + option + '</option>');
    }
  }

  var performTest = function(functionNumber) {
    reset(); // Reset previous test
    $("#tests").html(""); //Clean test results
    isNumber = functionsToTest[functionNumber]; // Override the isNumber global function with the one to test
    testSuite(); // Run the test

    // Get test results
    var totalFail = 0;
    var totalPass = 0;
    $("b.fail").each(function() {
      totalFail += Number($(this).html());
    });
    $("b.pass").each(function() {
      totalPass += Number($(this).html());
    });
    $("#testresult").html(totalFail + " of " + (totalFail + totalPass) + " test failed.");

    $("#banner").attr("class", "").addClass(totalFail > 0 ? "fail" : "pass");
  }

  return {
    performTest: performTest,
    fillToTestSelect: fillToTestSelect,
    testSuite: testSuite
  };
}();


$(document).ready(function() {
  testHelper.fillToTestSelect();
  testHelper.performTest(0);

  $("#toTest").change(function() {
    testHelper.performTest($(this).children(":selected").val());
  });
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js" type="text/javascript"></script>
<script src="https://rawgit.com/Xotic750/testrunner-old/master/testrunner.js" type="text/javascript"></script>
<link href="https://rawgit.com/Xotic750/testrunner-old/master/testrunner.css" rel="stylesheet" type="text/css">
<h1>isNumber Test Cases</h1>

<h2 id="banner" class="pass"></h2>

<h2 id="userAgent">Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.11 (KHTML, like Gecko) Chrome/23.0.1271.95 Safari/537.11</h2>

<div id="currentFunction"></div>

<div id="selectFunction">
  <label for="toTest" style="font-weight:bold; font-size:Large;">Select function to test:</label>
  <select id="toTest" name="toTest">
  </select>
</div>

<div id="testCode"></div>

<ol id="tests">
  <li class="pass">
    <strong>Integer Literals <b style="color:black;">(0, 10, 10)</b></strong>

    <ol style="display: none;">
      <li class="pass">Negative integer string</li>

      <li class="pass">Zero string</li>

      <li class="pass">Positive integer string</li>

      <li class="pass">Negative integer number</li>

      <li class="pass">Zero integer number</li>

      <li class="pass">Positive integer number</li>

      <li class="pass">Octal integer literal string</li>

      <li class="pass">Octal integer literal</li>

      <li class="pass">Hexadecimal integer literal string</li>

      <li class="pass">Hexadecimal integer literal</li>
    </ol>
  </li>

  <li class="pass">
    <strong>Foating-Point Literals <b style="color:black;">(0, 6, 6)</b></strong>

    <ol style="display: none;">
      <li class="pass">Negative floating point string</li>

      <li class="pass">Positive floating point string</li>

      <li class="pass">Negative floating point number</li>

      <li class="pass">Positive floating point number</li>

      <li class="pass">Exponential notation</li>

      <li class="pass">Exponential notation string</li>
    </ol>
  </li>

  <li class="pass">
    <strong>Non-Numeric values <b style="color:black;">(0, 18, 18)</b></strong>

    <ol style="display: none;">
      <li class="pass">Empty string: false</li>

      <li class="pass">Whitespace characters string: false</li>

      <li class="pass">Tab characters string: false</li>

      <li class="pass">Alphanumeric character string: false</li>

      <li class="pass">Non-numeric character string: false</li>

      <li class="pass">Boolean true literal: false</li>

      <li class="pass">Boolean false literal: false</li>

      <li class="pass">Number with preceding non-numeric characters: false</li>

      <li class="pass">Number with trailling non-numeric characters: false</li>

      <li class="pass">Undefined value: false</li>

      <li class="pass">Null value: false</li>

      <li class="pass">NaN value: false</li>

      <li class="pass">Infinity primitive: false</li>

      <li class="pass">Positive Infinity: false</li>

      <li class="pass">Negative Infinity: false</li>

      <li class="pass">Date object: false</li>

      <li class="pass">Empty object: false</li>

      <li class="pass">Instance of a function: false</li>
    </ol>
  </li>
</ol>

<div id="main">
  This page contains tests for a set of isNumber functions. To see them, take a look at the source.
</div>

<div>
  <p class="result">Tests completed in 0 milliseconds.
    <br>0 tests of 0 failed.</p>
</div>


예, 내장 isNaN(object) 은 정규식 구문 분석보다 훨씬 빠릅니다. 내장 해석되고 컴파일되지 않기 때문입니다.

결과가 찾고있는 것과 약간 다르지만 ( 시도해보십시오 ) :

                                              // IS NUMERIC
document.write(!isNaN('-1') + "<br />");      // true
document.write(!isNaN('-1.5') + "<br />");    // true
document.write(!isNaN('0') + "<br />");       // true
document.write(!isNaN('0.42') + "<br />");    // true
document.write(!isNaN('.42') + "<br />");     // true
document.write(!isNaN('99,999') + "<br />");  // false
document.write(!isNaN('0x89f') + "<br />");   // true
document.write(!isNaN('#abcdef') + "<br />"); // false
document.write(!isNaN('1.2.3') + "<br />");   // false
document.write(!isNaN('') + "<br />");        // true
document.write(!isNaN('blah') + "<br />");    // false


정수 값은 다음을 통해 확인할 수 있습니다.

function isNumeric(value) {
    var bool = isNaN(+value));
    bool = bool || (value.indexOf('.') != -1);
    bool = bool || (value.indexOf(",") != -1);
    return !bool;
};

이 방법은 더 쉽고 빠릅니다! 모든 테스트가 확인되었습니다!


추가 할 몇 가지 테스트 :

IsNumeric('01.05') => false
IsNumeric('1.') => false
IsNumeric('.') => false

나는 이것을 생각해 냈다.

function IsNumeric(input) {
    return /^-?(0|[1-9]\d*|(?=\.))(\.\d+)?$/.test(input);
}

솔루션은 다음을 포함합니다.

  • 처음에 선택적 음수 부호
  • 단일 0 또는 0으로 시작하지 않는 하나 이상의 숫자이거나 마침표 뒤에 오는 한 아무것도 없습니다.
  • 하나 이상의 숫자가 뒤 따르는 마침표

야후! UI 는 이것을 사용합니다 :

isNumber: function(o) {
    return typeof o === 'number' && isFinite(o);
}

isNaN 함수를 사용하십시오. !isNaN(yourstringhere) 테스트하면 이러한 상황에 적합합니다.


knockoutJs 내장 라이브러리 검증 기능

필드를 확장하면 필드가 검증됩니다.

1) 번호

self.number = ko.observable(numberValue) .extend ({번호 : true}) ;

테스트 케이스

numberValue = '0.0'    --> true
numberValue = '0'      --> true
numberValue = '25'     --> true
numberValue = '-1'     --> true
numberValue = '-3.5'   --> true
numberValue = '11.112' --> true
numberValue = '0x89f'  --> false
numberValue = ''       --> false
numberValue = 'sfsd'   --> false
numberValue = 'dg##$'  --> false

2) 숫자

self.number = ko.observable(numberValue) .extend ({숫자 : true}) ;

테스트 케이스

numberValue = '0'      --> true
numberValue = '25'     --> true
numberValue = '0.0'    --> false
numberValue = '-1'     --> false
numberValue = '-3.5'   --> false
numberValue = '11.112' --> false
numberValue = '0x89f'  --> false
numberValue = ''       --> false
numberValue = 'sfsd'   --> false
numberValue = 'dg##$'  --> false

3) 최소 및 최대

self.number = ko.observable(numberValue) .extend ({min : 5}). extend ({최대 : 10}) ;

이 필드는 5와 10 사이의 값만 허용합니다.

테스트 케이스

numberValue = '5'    --> true
numberValue = '6'    --> true
numberValue = '6.5'  --> true
numberValue = '9'    --> true
numberValue = '11'   --> false
numberValue = '0'    --> false
numberValue = ''    --> false

나는 이것이 여러 번 대답되었다는 것을 알고 있지만 다음은 일부 시나리오에서 유용 할 수있는 괜찮은 후보입니다.

'.42'는 숫자가 아니라고 '4'라고 가정합니다. 숫자가 아니므로이 점을 고려해야합니다.

function isDecimal(x) {
  return '' + x === '' + +x;
}

function isInteger(x) {
  return '' + x === '' + parseInt(x);
}

isDecimal다음과 같은 테스트를 통과 :

function testIsNumber(f) {
  return f('-1') && f('-1.5') && f('0') && f('0.42')
    && !f('.42') && !f('99,999') && !f('0x89f')
    && !f('#abcdef') && !f('1.2.3') && !f('') && !f('blah');
}

여기서의 아이디어는 모든 숫자 또는 정수에는 하나의 "정식"문자열 표현이 있으며 모든 비정규 표현은 거부되어야한다는 것입니다. 그래서 우리는 숫자로 캐스트하고 결과가 원래 문자열인지 확인합니다.

이러한 기능이 유용한 지 여부는 사용 사례에 따라 다릅니다. 한 가지 특징은 고유 문자열이 고유 숫자를 나타냅니다 (둘 다 isNumber()테스트를 통과 한 경우 ).

이는 객체 속성 이름과 같은 숫자와 관련이 있습니다.

var obj = {};
obj['4'] = 'canonical 4';
obj['04'] = 'alias of 4';
obj[4];  // prints 'canonical 4' to the console.

더 간단한 솔루션을 사용하고 있습니다.

function isNumber(num) {
    return parseFloat(num).toString() == num
}

여기에 정확한 jQuery의 변형 대신 사용하는 약간 개선 된 버전 (아마도 가장 빠른 방법)이 있습니다. 왜 그들이 이것을 사용하지 않는지 모르겠습니다.

function isNumeric(val) {
    return !isNaN(+val) && isFinite(val);
}

jQuery의 버전의 단점은 수치를 선도하고 같은 문자를 후행 문자열 전달하는 경우이다 "123abc"(가) parseFloat | parseInt밖으로 숫자 부분을 추출하고 123을 반환하되 것, 두 번째 가드 isFinite어쨌든 실패합니다. 단항 +연산자를 사용하면 +가 그러한 하이브리드에 NaN을 던지기 때문에 첫 번째 가드에서 죽을 것입니다.


false빈 문자열에 대한 답은 반환되지 않습니다 .

function is_numeric(n)
{
 return (n != '' && !isNaN(parseFloat(n)) && isFinite(n));
}

변수에 숫자처럼 보이는 문자열뿐만 아니라 유효한 숫자가 포함되어 있는지 확인하려면 Number.isFinite(value)사용할 수 있습니다.

이것은 ES2015 이후 언어의 일부입니다ES2015

예 :

Number.isFinite(Infinity)   // false
Number.isFinite(NaN)        // false
Number.isFinite(-Infinity)  // false

Number.isFinite(0)          // true
Number.isFinite(2e64)       // true

Number.isFinite('0')        // false
Number.isFinite(null)       // false

function IsNumeric(num) {
     return (num >=0 || num < 0);
}

이것은 0x23 타입 숫자에서도 작동합니다.


function inNumeric(n){
   return Number(n).toString() === n;
}

n이 숫자 Number(n)이면 숫자 값을 반환하고 toString()문자열로 다시 설정합니다. 그러나 n이 숫자 가 아닌 경우 원래 숫자 와 일치하지 않으므로 Number(n)반환 NaN됩니다.n





numbers