Проверить, содержит ли переменная числовое значение в Javascript?

В PHP это довольно просто:

is_numeric(23);//true
is_numeric("23");//true
is_numeric(23.5);//true
is_numeric(true);//false

Но как мне это сделать в Javascript? Я мог бы использовать регулярное выражение, но есть ли для этого функция?

Ответов (9)

Решение

Что о:

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

IsNaN встроенной функции используется для проверки , является ли значение не является числом.

Обновление: Кристоф прав, в JavaScript логические типы конвертируются в Number, возвращая 1 для истины и 0 для false, поэтому, если вы оцениваете, 1 + true результат будет 2.

Учитывая такое поведение, я обновил функцию, чтобы предотвратить преобразование логических значений в их числовое представление.

Вот что я придумал:

value = "2.34";
if (parseFloat(value).toString() === value) {
    alert("number");
}

Это должно работать с числами с плавающей запятой и целыми числами, положительными и отрицательными. Я не знаю о бесконечности, как уже говорилось в некоторых ответах выше.

Если ваше значение может быть числом, а не всегда строкой, вы можете изменить === на ==, и он будет обрабатывать и то, и другое.

Вот несколько тестов для isNaN vs. isFinite и typeof === "number"

http://jsperf.com/isnan-vs-isfinite-vs/3

Видимо typeof === "number" примерно в 5 раз быстрее

Вот мое решение: ES6 / 2015

Отказ от ответственности : это решение работает только в том случае, если пользователь отправляет тип числа в качестве ввода. Например: 23 - это числовой тип, но «23» - это не числовой тип, это строковый тип.

function isValidNumber(value) {
  return typeof value === 'number' && Number.isNaN(value) === false;
}

Тестовые кейсы

isValidNumber(10) // true
isValidNumber(10.34) // true
isValidNumber('geo10') // false
isValidNumber('10geo') // false
isValidNumber('') // false
isValidNumber(NaN) // false
isValidNumber(true) // false
isValidNumber(false) // false

Запустите фрагмент кода, чтобы увидеть сравнение наиболее популярных ответов по этой теме.

Некоторые тестовые примеры не выделяются (и не вносят вклад в сводку). Эти случаи помечены как неоднозначные, потому что неясно, следует ли считать данное значение числом.

// Each of these functions should output a truthy/falsy value if the input is
// a number
const solutionsToTest = [
  v => parseFloat(v),
  v => Number(v),
  v => !isNaN(v),
  v => typeof v != "boolean" && !isNaN(v),
  v => isFinite(String(v)),
  v => !isNaN(parseFloat(v)) && isFinite(v)
];

const testCases = [
  //[ Test Name, Test Value, Expected Output, Is Ambiguous ]

  // Whitespace
  ['""', "", false, false],
  ['"\\t"', "\t", false, false],
  ['" "', " ", false, false],

  // Infinity
  ['"Infinity"', "Infinity", false, true],
  ['"+Infinity"', "Infinity", false, true],
  ["-Infinity", -Infinity, false, true],
  ["Infinity", Infinity, false, true],

  // Numbers mixed with symbols
  ['"123abc"', "123abc", false, true],
  ['"abc123"', "abc123", false, false],
  ['".0."', ".0.", false, false],
  ['"1."', "1.", true, true],
  ['"."', ".", false, true],
  ['"01"', "01", true, true],
  ['"-0"', "-0", true, true],
  ["+1", +1, true, true],
  ["-1", -1, true, true],

  // Other js types
  ["'null'", "null", false, false],
  ["'true'", "true", false, false],
  ["'false'", "false", false, false],
  ["null", null, false, false],
  ["true", true, false, false],
  ["false", false, false, false],
  ["NaN", NaN, false, false],
  ["[]", [], false, false],
  ["{}", {}, false, false],
  ["/./", /./, false, false],
  ["() => {}", () => {}, false, false]
];

const styles = {
  code: {
    fontFamily: "monospace",
    fontSize: 16
  },
  success: {
    backgroundColor: "#00ff5478"
  },
  failure: {
    backgroundColor: "#ff00008c"
  }
};

class TestCaseTable extends React.Component {
  static renderTableHeader(solutionsToTest) {
    return (
      <tr>
        <th>
          <p>Test Case</p>
        </th>
        {solutionsToTest.map(f => (
          <th key={f.toString()}>
            <p style={styles.code}>{f.toString()}</p>
          </th>
        ))}
      </tr>
    );
  }
  static renderTableRow(testCase, solutionsToTest) {
    const [testName, input, expectedOutput, isAmbiguous] = testCase;
    return (
      <tr key={testName}>
        <td style={styles.code}>{testName}</td>
        {solutionsToTest.map(f => {
          const output = Boolean(f(input));
          const style = isAmbiguous
            ? {}
            : output == expectedOutput ? styles.success : styles.failure;
          return (
            <td style={style} key={f.toString()}>
              <p>{output + ""}</p>
            </td>
          );
        })}
      </tr>
    );
  }
  render() {
    // Sort test cases, put the ambiguous ones after (but maintain stable sort
    // order)
    let sortedCases = [
      ...testCases.filter(([a, b, c, ambiguous]) => !ambiguous),
      ...testCases.filter(([a, b, c, ambiguous]) => ambiguous)
    ];
    return (
      <table>
        <thead>{TestCaseTable.renderTableHeader(solutionsToTest)}</thead>
        <tbody>
          {sortedCases.map(tc =>
            TestCaseTable.renderTableRow(tc, solutionsToTest)
          )}
        </tbody>
      </table>
    );
  }
}
class TestCaseSummaryTable extends React.Component {
  renderTableHeader(solutionsToTest) {
    return (
      <tr>
        <th>Summary</th>
        {solutionsToTest.map(f => (
          <th key={f.toString()}>
            <p style={styles.code}>{f.toString()}</p>
          </th>
        ))}
      </tr>
    );
  }
  renderSuccessRateRow(solutionsToTest, testCases) {
    // Ignore potentially ambiguous test cases
    testCases = testCases.filter(
      ([name, input, expected, ambiguous]) => !ambiguous
    );

    const numSuccess = testSolution =>
      testCases.reduce((succeeded, [name, input, expected]) => {
        return succeeded + (Boolean(testSolution(input)) == expected ? 1 : 0);
      }, 0);

    return (
      <tr>
        <td>
          <p>Test Success</p>
        </td>
        {solutionsToTest.map(f => (
          <td>
            <p>
              {numSuccess(f)} / {testCases.length}
            </p>
          </td>
        ))}
      </tr>
    );
  }
  render() {
    return (
      <table>
        <thead>{this.renderTableHeader(solutionsToTest)}</thead>
        <tbody>{this.renderSuccessRateRow(solutionsToTest, testCases)}</tbody>
      </table>
    );
  }
}

const root = () => {
  return (
    <div>
      <TestCaseSummaryTable />
      <TestCaseTable />
    </div>
  );
};

ReactDOM.render(root(), document.querySelector("#application"));
td {
  text-align: center;
  vertical-align: middle;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
<div id="application"></div>

function is_numeric(val) {
  return ((+val) == val);
}

Это должно делать свое дело.

Это проверяет числовые значения, включая отрицательные числа и числа с плавающей запятой.

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

@Vordreller: я исправил Regex. Теперь он должен работать правильно.

Для проверки типов в javascript вы можете использовать typeof оператор:

js> var x = 1;
js> typeof(x);
number

Так:

if (typeof(x) === 'number') {
   // Do something
}

Если вы хотите привести значение переменной к целому числу, вы можете использовать, parseInt(x, 10) который будет анализировать значение как целое число с основанием 10. Точно так же вы можете использовать, parseFloat если хотите значение с плавающей запятой. Тем не менее, они всегда будут принуждать независимо от типа так прохождения null, true и т.д. всегда будет возвращать число. Однако вы можете проверить, действителен ли это номер, позвонив isNaN .

Итак, собираем все вместе:

!isNaN(parseFloat(23)) // true
!isNaN(parseFloat('23')) // true
!isNaN(parseFloat(23.5)) // true
!isNaN(parseFloat(true)) // false

или

function isNumber(x) {
    return !isNaN(parseFloat(x));
}

Я не думаю, что до сих пор ни одно из предложений действительно работает. Например

!isNaN(parseFloat(foo))

нет, потому что parseFloat() игнорирует завершающие нечисловые символы.

Чтобы обойти это, вы можете сравнить возвращаемое значение с тем, которое было возвращено преобразованием с помощью Number() (или, что эквивалентно, с использованием унарного преобразования +, но я предпочитаю явное преобразование):

parseFloat(foo) === Number(foo)

Это все равно будет работать, если обе функции вернутся, NaN потому что NaN !== NaN есть true .

Другая возможность - сначала преобразовать в строку, затем в число, а затем проверить NaN, т.е.

!isNaN(Number(String(foo)))

или эквивалентно, но менее читабельно (но, скорее всего, быстрее)

!isNaN(+('' + foo))

Если вы хотите исключить бесконечные значения, используйте isFinite() вместо !isNaN(), т.е.

isFinite(Number(String(foo)))

Явное приведение с помощью перехода на Number() самом деле не требуется , потому что isNan() и isFinite() приведение к числу неявно - вот почему !isNaN() не работает!

На мой взгляд, наиболее подходящим решением было бы

isFinite(String(foo))

Как отметил Мэтью, второй подход не обрабатывает строки, которые содержат только пробелы.

Исправить несложно - используйте код из комментария Мэтью или

isFinite(String(foo).trim() || NaN)

Вам нужно будет решить, лучше ли это, чем сравнивать результаты parseFloat() и Number() .