JavaScriptで10進数を検証する-IsNumeric()


2376

JavaScriptで10進数を検証する最もクリーンで効果的な方法は何ですか?

ボーナスポイント:

  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

256
ノート99,999はフランスでは有効な数値であり、uk / us形式の99.999と同じであるため、たとえば入力フォームから文字列を読み取っている場合、99,999はtrueになる可能性があります。
2008


79
10進数のコンマは、ヨーロッパとロシア(英国を除く)全体で標準です
カルマリウス

90
jQueryの1.7を導入しましたjQuery.isNumeric:ユーティリティ関数api.jquery.com/jQuery.isNumeric
ATES Goral

24
jQuery.isNumericOPの7番目のテストケースに失敗しIsNumeric('0x89f') => *false*ます()。ただし、このテストケースに同意するかどうかはわかりません。
Tim Lehner、2012

回答:


2898

@ジョエルの答えはかなり近いですが、次の場合には失敗します:

// Whitespace strings:
IsNumeric(' ')    == true;
IsNumeric('\t\t') == true;
IsNumeric('\n\r') == true;

// Number literals:
IsNumeric(-1)  == false;
IsNumeric(0)   == false;
IsNumeric(1.1) == false;
IsNumeric(8e5) == false;

少し前にIsNumeric関数を実装しなければなりませんでした。変数に数値が含まれているかどうかを調べるために、その型関係なくString、数値を含む(指数表記なども考慮する必要がありました)、Numberオブジェクト、事実上何でもその関数に渡すことができ、型の強制を処理して、型の仮定を行うことができませんでした(たとえば+true == 1;trueと見なすべきではありません"numeric")。

多数の関数実装に対して行われたこの+30ユニットテストのセットを共有する価値があると思います。また、すべてのテストに合格したものも共有します。

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

PS isNaNisFiniteは、数値への強制変換が原因で混乱する動作をします。ES6では、Number.isNaNNumber.isFiniteがこれらの問題を修正します。それらを使用する場合は、そのことを覚えておいてください。


更新jQueryがこれを実行する方法を次に示します(2.2-stable)

isNumeric: function(obj) {
    var realStringObj = obj && obj.toString();
    return !jQuery.isArray(obj) && (realStringObj - parseFloat(realStringObj) + 1) >= 0;
}

アップデートAngular 4.3

export function isNumeric(value: any): boolean {
    return !isNaN(value - parseFloat(value));
}

26
これは、10進数のコンマを使用する他のロケールでは失敗しますが、 `n = n.replace(/、/、"。 "); 'を追加します。それを修正するために戻る前に。
Zoltan Lengyel

5
@RobG、その挙動は、意図的である2e308 > Number.MAX_VALUEことから2e308 == Infinitytrue正と負の無限大の値についても返す関数が必要な場合は、テストスイートの関数No. 2を確認してください。乾杯。
CMS 2011年

39
ところで、ユニットテストはjQueryプロジェクト
CMS

7
jQueryもこの実装を使用しています。
RichardTowers

4
ここでの解決策は、JQueryを使用することです。彼らはこれのより良い実装を今持っています:github.com/jquery/jquery/blob/master/src/core.js#L230
Robert Massaioli 2013年

337

あっ!正規表現の答えを聞かないでください。RegExはこれに不快で、パフォーマンスだけを話しているのではありません。正規表現の間違いを見つけるのは簡単ではありません。

を使用できない場合isNaN()、これははるかにうまく機能するはずです。

function IsNumeric(input)
{
    return (input - 0) == input && (''+input).trim().length > 0;
}

仕組みは次のとおりです。

(input - 0)JavaScriptは、あなたの入力値に型強制を行うための表現力。最初に、減算演算の数値として解釈する必要があります。数値への変換が失敗した場合、式はになりNaNます。この数値結果は、渡された元の値と比較されます。左側が数値になっているため、型強制が再び使用されます。両側からの入力が同じ元の値から同じ型に強制変換されたので、それらは常に同じである(常に真)と考えられます。ただし、NaNと等しくないことを示す特別なルールがあるNaNため、数値に変換できない値(および数値に変換できない値のみ)はfalseになります。

長さのチェックは、空の文字列が関係する特別な場合のためのものです。また、これは0x89fテストで低下することにも注意してください。これは、多くの環境で数値リテラルを定義する適切な方法だからです。その特定のシナリオをキャッチしたい場合は、追加のチェックを追加できます。さらに良いことに、それが使用しない理由である場合はisNaN()、独自の関数をラップするだけでisNaN()追加のチェックを実行できます。

要約すると、値を数値に変換できるかどうかを知りたい場合は、実際に数値に変換してみてください。


私は戻って、なぜ空白文字列に期待された出力がなかったのかについていくつか調査しました、そして私はそれを今得たと思います:空の文字列は強制されます0ではなくNaN。長さチェックの前に文字列をトリミングするだけでこのケースを処理できます。

ユニットテストを実行すると、新しいコードに対してテストが実行され、無限リテラルとブールリテラルでのみ失敗します。問題になるのは、コードを生成している場合だけです(実際、リテラルを入力して数値かどうかを確認するのは誰ですか?知っておくべき)、そしてそれは生成する奇妙なコードになるでしょう。

しかし、繰り返しますが、これを使用する唯一の理由は、何らかの理由でisNaN()を避けなければならない場合です。


28
これは、空白文字列では失敗します。たとえばIsNumeric(' ')IsNumeric('\n\t')などがすべて返されますtrue
Crescent Fresh

29
また、Numberリテラルが失敗すると、IsNumeric(5) == false;私が投稿した単体テストのセットをチェックし16ます。この関数は、テストスイートの番号です。stackoverflow.com/questions/18082/...
CMS

20
正規表現を使用しないことについて警告した後、正規表現(置換)の使用を誰も指摘しなかったなんて信じられません...確かに、空白の置換は数値解析よりも簡単ですが、それでも間違いなく「厄介」です。
Patrick M

1
@オリオールそれは大きな問題です...その日以降にセキュリティ修正がリリースされていないため、XPからの脱却が優先されるべきです。
Joel Coehoorn 2013年

1
@Oriol XPかどうか、IE8以下を使用している場合、恐ろしく時代遅れのソフトウェアを使用しています。許可されたXPではIE9 +を実行できないため、ChromeまたはFFを使用してください。IE8を使用して過去に住んでいる人々は、多くのWeb開発者の存在の悩みの種です。完全に優れたコードがIE8でも実行されることを確認するのに費やした時間があるとしたら、FFとChromeで動作するコードを取得し、IE8で実行するようにパッチを当てることは、Windows 8実行可能ファイルを取得するのと同じくらい実用的です。 Windows 3.1でも同じように動作することを確認してください。
chiliNUT 14

70

この方法はうまくいくようです:

function IsNumeric(input){
    var RE = /^-{0,1}\d*\.{0,1}\d+$/;
    return (RE.test(input));
}

1行で:

const IsNumeric = (num) => /^-{0,1}\d*\.{0,1}\d+$/.test(num);

そしてそれをテストするには:

const IsNumeric = (num) => /^-{0,1}\d*\.{0,1}\d+$/.test(num);
    
    function TestIsNumeric(){
        var results = ''
        results += (IsNumeric('-1')?"Pass":"Fail") + ": IsNumeric('-1') => true\n";
        results += (IsNumeric('-1.5')?"Pass":"Fail") + ": IsNumeric('-1.5') => true\n";
        results += (IsNumeric('0')?"Pass":"Fail") + ": IsNumeric('0') => true\n";
        results += (IsNumeric('0.42')?"Pass":"Fail") + ": IsNumeric('0.42') => true\n";
        results += (IsNumeric('.42')?"Pass":"Fail") + ": IsNumeric('.42') => true\n";
        results += (!IsNumeric('99,999')?"Pass":"Fail") + ": IsNumeric('99,999') => false\n";
        results += (!IsNumeric('0x89f')?"Pass":"Fail") + ": IsNumeric('0x89f') => false\n";
        results += (!IsNumeric('#abcdef')?"Pass":"Fail") + ": IsNumeric('#abcdef') => false\n";
        results += (!IsNumeric('1.2.3')?"Pass":"Fail") + ": IsNumeric('1.2.3') => false\n";
        results += (!IsNumeric('')?"Pass":"Fail") + ": IsNumeric('') => false\n";
        results += (!IsNumeric('blah')?"Pass":"Fail") + ": IsNumeric('blah') => false\n";
        
        return results;
    }

console.log(TestIsNumeric());
.as-console-wrapper { max-height: 100% !important; top: 0; }

その正規表現をhttp://www.codetoad.com/javascript/isnumeric.aspから借りました。説明:

/^ match beginning of string
-{0,1} optional negative sign
\d* optional digits
\.{0,1} optional decimal point
\d+ at least one digit
$/ match end of string

1
// ALSO SHOULD BE ADD ADD YOUR TEST results + =(!IsNumeric( '-')? "Pass": "Fail")+ ":IsNumeric( '-')=> false \ n"; 結果+ =(!IsNumeric('01 ')? "Pass": "Fail")+ ":IsNumeric('01')=> false \ n"; 結果+ =(!IsNumeric( '-01')? "Pass": "Fail")+ ":IsNumeric( '-01')=> false \ n"; 結果+ =(!IsNumeric( '000')? "Pass": "Fail")+ ":IsNumeric( '000')=> false \ n";
Dan

これは何をしますか?/ ^-{0,1} \ d * \。{0,1} \ d + $ /
call-me

「{0,1}」を「?」に置き換えることができるため、正規表現は次のようになります:/^-?\d*\.?\d+$/?
2016年

素晴らしくてシンプル。
ブレーカー

53

Yahoo! UIはこれを使用します。

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

25
これは、数値の内容ではなく、変数の型をよりチェックすることです。で作成された数値でも失敗しますnew Number(1)
アレックス

4
アレックスが言うように、これは実際の質問には答えません。これは、o = "1001"の場合は失敗するためです。
ケース

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

これは、0x23タイプの数値でも機能します。


29
IsNumeric('')IsNumeric(' ')IsNumeric(true)IsNumeric(false)IsNumeric(null)返すtrue代わりにfalse
Oriol 2013

49

受け入れられた答えはあなたのテスト#7に失敗しました、そして私はあなたがあなたの考えを変えたからだと思います。これは、私が問題を抱えていた、受け入れられた回答への応答です。

一部のプロジェクトでは、いくつかのデータを検証し、それが数学演算で使用できるjavascriptの数値であることをできる限り確認する必要がありました。

jQuery、およびその他の一部のJavaScriptライブラリには、通常と呼ばれるこのような関数がすでに含まれていisNumericます。前述のライブラリが使用しているのと同じ一般的なルーチンである、回答として広く受け入れられているstackoverflowに関する投稿もあります。

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);
}

もちろん、代わりにArray.isArray、jquery、$.isArrayまたはプロトタイプを使用することもできますObject.isArrayObject.prototype.toString.call(n) !== '[object Array]'

2番目の問題は、負の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, ''));
  };
}());

次に、CMS +30のテストケースを取り、jsfiddleテストを複製して、追加のテストケースと上記のソリューションを追加しました。

広く受け入れられ使用されている答えに取って代わるものではないかもしれませんが、これがisNumeric関数の結果として期待しているものよりも多い場合は、これが何らかの助けになると期待しています。

編集: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>


2
これは私の考えでは最もシールドされた機能です。最後のもの。受け入れられた回答はおそらくすべてのケースの99.99%をカバーしますが、これはおそらくa)わずかなオーバーヘッドのケースの100%を持っています。
サミュエル

"99,999"の浮動小数点リテラルを忘れました。これは、英国を除くすべてのヨーロッパで有効な番号です
Andrii Horda 2016年

それは忘れられなかった、それは私がJavascriptの数値の意味で数値と見なしたものではなかった、OPも述べたIsNumeric('99,999') => false
Xotic750

34

そうです、組み込み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

18

関数を使用しますisNaN。あなたが!isNaN(yourstringhere)それをテストすれば、これらの状況のいずれでもうまく機能すると信じています。


注:!isNaN(null)== true(Number(null)== 0以降)
Jonathan Lonowski 2008年

if(!(x == null || isNaN(x)))alert( "isNumeric"); //しかし、このソリューションは0x40を受け入れるため、オペレーションが望んだものではありません。
いくつかの

isNaN( "Infinity")=== falseであることに注意してください。これもおそらく望んでいることではありません(しかし、実際には起こりません)。
Erik Hesselink、2010

16

jQuery 1.7以降、以下を使用できますjQuery.isNumeric()

$.isNumeric('-1');      // true
$.isNumeric('-1.5');    // true
$.isNumeric('0');       // true
$.isNumeric('0.42');    // true
$.isNumeric('.42');     // true
$.isNumeric('0x89f');   // true (valid hexa number)
$.isNumeric('99,999');  // false
$.isNumeric('#abcdef'); // false
$.isNumeric('1.2.3');   // false
$.isNumeric('');        // false
$.isNumeric('blah');    // false

あなたが言ったこととは異なり0x89f、有効な数値です(ヘキサ)


OPは有効な10進数を必要とするため、jQuery isNumeric適していません。非常に大きな数の場合も失敗します。
RobG、2015年

13

それはRegExpなしで行うことができます

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

5
==を使用している場合は、文字列として表示された数値でもtrueを返します。したがって、「==」の場合、「42」は有効な数としてカウントされ、===の場合、無効としてカウントされます
Aquatic

これは、「-0。」、「-。0」、「。0」、および「0」でtrueを返します。
Janus Troelsen 2012


8
return (input - 0) == input && input.length > 0;

うまくいきませんでした。警告を入れてテストしたところ、input.lengthでしたundefined。整数の長さをチェックするプロパティはないと思います。だから私がしたことは

var temp = '' + input;
return (input - 0) == input && temp.length > 0;

それはうまくいきました。


7

私が間違っていない場合、これは定数(InfinityNaN)と符号演算子+/ を除く、有効なJavaScriptの数値と一致するはずです。-限り、これらは実際には数値の一部ではないため、これらは別個の演算子です)。

評価のためにJavaScriptに数値を送信することはオプションではなかったトークナイザーにこれが必要でした...それは間違いなく可能な限り最短の正規表現ではありませんが、JavaScriptの数値構文のすべての細かい微妙さをキャッチしていると思います。

/^(?:(?:(?:[1-9]\d*|\d)\.\d*|(?:[1-9]\d*|\d)?\.\d+|(?:[1-9]\d*|\d)) 
(?:[e]\d+)?|0[0-7]+|0x[0-9a-f]+)$/i

有効な数は次のとおりです。

 - 0
 - 00
 - 01
 - 10
 - 0e1
 - 0e01
 - .0
 - 0.
 - .0e1
 - 0.e1
 - 0.e00
 - 0xf
 - 0Xf

無効な数値は

 - 00e1
 - 01e1
 - 00.0
 - 00x0
 - .
 - .e0

7

@CMSの答えで私が抱えていた唯一の問題はNaN、Infinity の除外です。これは、多くの状況で役立つ数値です。をチェックする1つの方法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は、別のエレガントな回答にかなり近いですが、16進数やその他の数値の文字列表現を処理します。


6

私にとって、これは最良の方法です:

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

残念ながら、これは「0」等...のように、数字のみの文字を含む任意の文字列を失敗しますちょっとSTRICT数値チェッカーです
アルマンMcHitarian

6

以下を追加します。

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

正の16進数はで始まり0x、負の16進数はで始まり-0xます。正の10進数はで始まり0、負の8進数はで始まり-0ます。これは、すでに言及されていることのほとんどを考慮に入れていますが、16進数と8進数、負の科学、無限大を含み、10進数の科学を削除して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));
}

6

ここではparseFloat関数ですべての作業を実行できると思います。以下の関数は、このページのすべてのテストに合格しますisNumeric(Infinity) == true

function isNumeric(n) {

    return parseFloat(n) == n;
}

はい、私もこの結論に達しました。この方法を使用して配列を処理する方法もとても気に入っています。単一の値を持つ配列はその値としてカウントされますが、それ以外はすべて失敗します。IsNumeric([3]) == true; IsNumeric([]) == false; IsNumeric([3, 4]) == false; しかし、それ は好みの問題だと思います!
Mark Birbeck

4

追加するいくつかのテスト:

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

私はこれを思いつきました:

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

ソリューションは以下をカバーします:

  • 先頭にオプションの負符号
  • 1つのゼロ、または0で始まらない1つ以上の数字、またはピリオドが続く限り何もない
  • 1つ以上の数字が続くピリオド

4

整数値は次の方法で確認できます。

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

この方法は簡単で高速です!すべてのテストがチェックされます!


4

ここに私がjQueryの正確なバリアントの代わりに使用する少し改善されたバージョン(おそらくそこにある最も速い方法)がありますが、なぜこれを使用しないのか本当にわかりません:

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

jQueryのバージョンの欠点は、あなたが数字をリードするなどの文字を末尾の文字列を渡した場合ということですアウトの数値部分を抽出し、123を返しますが、されますが、第2のガードはとにかくそれを失敗します。+はそのようなハイブリッドに対してNaNをスローするので、単項演算子を使用すると、最初のガードで死ぬでしょう:)少しのパフォーマンスですが、確かなセマンティックゲインはあると思います。"123abc"parseFloat | parseIntisFinite+


2
単項 '+'がオブジェクトに対してvalueOf()を呼び出すことに注意してください-このjsfiddleを参照してください。また、これは先頭の空白も先頭の回答と同様に失敗します。
イヤカム2013

3

私の解決策、

function isNumeric(input) {
    var number = /^\-{0,1}(?:[0-9]+){0,1}(?:\.[0-9]+){0,1}$/i;
    var regex = RegExp(number);
    return regex.test(input) && input.length>0;
}

それはあらゆる状況で機能するように見えますが、私は間違っているかもしれません。


その正規表現は、不必要に文字をエスケープする必要がなければ、混乱しにくくなります。for およびforを使用?してください。また、それをでラップすると、(非)キャプチャグループを使用したり忘れたりすることができます。{0,1}\d[0-9]+(?:){0,1}*
アレックス


3

これはうまくいくはずです。ここに提供されている関数の一部には欠陥があり、ここにある他の関数よりも高速である必要があります。

        function isNumeric(n)
        {
            var n2 = n;
            n = parseFloat(n);
            return (n!='NaN' && n2==n);
        }

説明:

自身のコピーを作成し、数値を浮動小数点数に変換してから、それがまだ数値である場合(整数または浮動小数点数)、それ自体を元の数値と比較し、元の数値と一致します。つまり、実際に数値です。

これは、数値文字列と単純な数値で機能します。16進数では機能しません。

警告:自己責任で使用してください。保証はありません。


4
自己責任で使用してください。作成者が確信していないコードを使用しないこと保証するものではありません;)
alex

1
@アレックス、少なくとも物事についてあなた自身の意見があります。いつも批判するだけではありません。
Stewart Mbofana 2014年

3

false空の文字列に対して返される回答はありません。その修正...

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

3

変数に数値のように見える文字列だけでなく、有効な数値が含まれているかどうかを確認するには、 Number.isFinite(value)使用できます。

これは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

1
多くの人が、ユーザー入力(通常は文字列)を解析するためにこの質問を参照すると思います。例に正しくリストされているため、この回答は失敗します。例:Number.isFinite('0') -> false
Michael Haren

あなたは完全に正しいです。私はこれを明確に表にしてみました。
adius

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

nが数値の場合Number(n)、数値を返し、toString()それを文字列に戻します。ただし、nが数値でない場合Number(n)は返されるNaNため、元の値と一致しませんn


このコードスニペットは問題を解決する可能性がありますが、説明を含めると、投稿の品質を向上させるのに役立ちます。あなたは将来の読者のための質問に答えていることを覚えておいてください、そしてそれらの人々はあなたのコード提案の理由を知らないかもしれません。また、コードと説明の両方の読みやすさが低下するため、コードを説明コメントで混雑させないようにしてください。
さようならStackExchange 2016

2

これは何度も回答されていると思いますが、以下は、いくつかのシナリオで役立つ、適切な候補です。

「.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');
}

ここでの考え方は、すべての数値または整数には1つの「正規」文字列表現があり、すべての非正規表現は拒否されるべきであるということです。したがって、数値にキャストして戻り、結果が元の文字列かどうかを確認します。

これらの機能が役立つかどうかは、ユースケースによって異なります。1つの特徴は、個別の文字列が個別の数値を表すことです(両方がisNumber()テストに合格した場合)。

これは、たとえばオブジェクトのプロパティ名としての数値に関連します。

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

2

knockoutJs Inbuildライブラリ検証関数

それを拡張することにより、フィールドは検証されます

1)番号

self.number = ko.observable(numberValue).extend({number: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({digit: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({max:10}) ;

このフィールドは5〜10の値のみを受け入れます

テストケース

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

2

小数の特別なセットを検証する必要がある場合は、次の単純なJavaScriptを使用できます。

http://codesheet.org/codesheet/x1kI7hAD

<input type="text" name="date" value="" pattern="[0-9]){1,2}(\.){1}([0-9]){2}" maxlength="6" placeholder="od npr.: 16.06" onchange="date(this);" />

JavaScript:

function date(inputField) {        
  var isValid = /^([0-9]){1,2}(\.){1}([0-9]){2}$/.test(inputField.value);   
  if (isValid) {
    inputField.style.backgroundColor = '#bfa';
  } else {
    inputField.style.backgroundColor = '#fba';
  }
  return isValid;
}

2

isNumeric=(el)=>{return Boolean(parseFloat(el)) && isFinite(el)}

大きな違いはありませんが、ブールコンストラクタを使用できます

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.