JavaScript: создание функции проверки чисел без jQuery
Быстрый ответ
Для достижения точности, аналогичной функции isNumeric()
в jQuery, предлагается следующая реализация:
function isNumeric(value) {
return Number.isFinite(value) || (typeof value === 'string' && value.trim() !== '' && Number.isFinite(Number(value)));
}
Проведенная проверка корректно обращается как с числами, так и со строками, которые содержат числа:
console.log(isNumeric(123)); // true
console.log(isNumeric('123')); // true
console.log(isNumeric(' ')); // false
console.log(isNumeric('123e-5')); // true
Приведенное решение использует функцию Number.isFinite()
, проверяющую, является ли значение числовым, и преобразует строки, позволяя распознавать числа в текстовом формате.
Почему следует избегать использования parseInt и какие минусы у isNaN?
Использование функции parseInt('123px')
в нашем алгоритме вернет 123
, что будут недопустимо, так как мы получим результат, являющийся ложноположительным. Для избежания такой ситуации, мы преобразуем строку в число и проверяем, соответствует ли оно всей структуре числового значения, удаляя при этом нежелательные символы.
Осторожно: Функцию isNaN()
можно расценить, как будто isNaN('123')
не равно NaN, поскольку она возвращает false, тогда как Number.isNaN()
строго возвращает true только для NaN. В нашем случае предпочтение отдается функции Number.isFinite()
, которая оказывается более точной и объединяет свойства обоих вышеупомянутых методов.
Точность работы с десятичными числами и различными числовыми форматами
Для точного определения десятичных чисел и распознавания разных числовых форматов, включая экспоненциальное представление, наш метод рассчитывает на использование parseFloat()
. Это позволяет анализировать не только целые числа, но и числа с плавающей точкой.
Эффективность функции-валидатора без зависимостей
Наша функция isNumeric
становится независимой реализацией валидации. Это позволяет упростить код, убрав его зависимость от jQuery, что делает кодовую базу более ясной и эффективной.
Обработка специфических числовых случаев
Такие особые числовые случаи, как Infinity
и NaN
, несмотря на их числовое происхождение, обрабатываются корректно. Функция Number.isFinite()
обеспечивает положительный результат проверки только для конкретных чисел, исключая любые математические моменты, которые могут вызвать путаницу при рассчётах.
Визуализация
Рассмотрим функцию isNumeric как Фильтр Типов (🔍), производящий отбор в Цифровом Пространстве (🔢):
**Фильтр (🔍):** функция isNumeric()
**Пространство (🔢):** [42, '42', 'сорок два', 3.14, NaN, undefined, '']
Процесс Фильтрации:
1. Отсеивает каждый элемент 🔎
2. Отмечает числа и строки, содержащие числа 🎯
3. Изъятие потенциальных проблемных мест 🚫
Результаты:
Прошли фильтр 🔍: [42, '42', 3.14]
Не прошли фильтр 🚫: ['сорок два', NaN, undefined, '']
Регулярные выражения для повышения точности
Для улучшения определения числовых значений в строках, можно использовать регулярные выражения. Они позволяют отсеивать некорректно форматированные десятичные числа, одновременно пропуская действительные, например:
function isReallyNumeric(n) {
return /^-?\d+(\.\d+)?$/.test(n) || (!isNaN(parseFloat(n)) && isFinite(n));
}
Усовершенствование: от isNumeric к Number.isNumeric
Добавьте в ваш JavaScript-код метод Number.isNumeric, чтобы он стал ещё более элегантным. Но только не упоминайте об этом перед Дугласом Крокфордом.
Number.isNumeric = Number.isNumeric || function(value) {
return (typeof value === 'number' || typeof value === 'string' && value.trim() !== '') && !isNaN(Number(value));
};
Совет: isNumeric
определяет "числовые эквиваленты", такие как "123". Это оказывается полезным при применении метода утиной типизации. Грамотное использование этого подхода усиливает гибкость динамично типизированного JavaScript, но будьте аккуратны и избегайте непредвиденных последствий!
Как избежать ложноположительных результатов
Есть искушение проверить, является ли строка числом, просто применив к ней + '123'
, однако это делать не следует. Это не будет работать с пустыми строками (+ '' === 0
), и это для нас недопустимо.