Как проверить, содержит ли строка только цифры в Java

В Java для класса String существует метод, называемый match, как использовать этот метод, чтобы проверить, имеет ли моя строка только цифры с регулярным выражением. Я пробовал с примерами ниже, но оба они вернули мне ложные результаты.

String regex = "[0-9]";
String data = "23343453";
System.out.println(data.matches(regex));

String regex = "^[0-9]";
String data = "23343453";
System.out.println(data.matches(regex));

Ответ 1

Попробуйте

String regex = "[0-9]+";

или

String regex = "\\d+";

Согласно регулярным выражениям Java, + означает "один или несколько раз", а \d означает "цифра".

Примечание. "Двойная обратная косая черта" является escape-последовательностью для получения одной обратной косой черты, поэтому \\d в строке Java дает фактический результат: \d

Ссылки:


Изменить: из-за некоторой путаницы в других ответах я пишу тестовый пример и подробно объясню некоторые вещи.

Во-первых, если вы сомневаетесь в правильности этого решения (или других), запустите этот тестовый пример:

String regex = "\\d+";

// positive test cases, should all be "true"
System.out.println("1".matches(regex));
System.out.println("12345".matches(regex));
System.out.println("123456789".matches(regex));

// negative test cases, should all be "false"
System.out.println("".matches(regex));
System.out.println("foo".matches(regex));
System.out.println("aa123bb".matches(regex));

Вопрос 1:

Разве нет необходимости добавлять ^ и $ в регулярное выражение, чтобы оно не совпадало с "aa123bb"?

Нет. В java метод matches (который был указан в вопросе) соответствует полной строке, а не фрагментам. Другими словами, нет необходимости использовать ^\\d+$ (хотя это также правильно). Пожалуйста, посмотрите последний негативный тестовый пример.

Обратите внимание, что если вы используете онлайн-проверку "регулярных выражений", это может вести себя по-другому. Для сопоставления фрагментов строки в Java вы можете использовать метод find, который подробно описан здесь:

Разница между match() и find() в Java Regex

Вопрос 2:

Разве это регулярное выражение не будет соответствовать пустой строке, ""? *

Нет. Регулярное выражение \\d* будет соответствовать пустой строке, но \\d+ - нет. Звезда * означает ноль или более, тогда как плюс + означает один или более. Пожалуйста, посмотрите первый отрицательный тестовый пример.

Вопрос 3

Не быстрее ли скомпилировать шаблон регулярных выражений?

Да. Действительно быстрее один раз скомпилировать шаблон регулярных выражений, чем при каждом вызове matches, и поэтому, если это влияет на производительность, тогда Pattern можно скомпилировать и использовать следующим образом:

Pattern pattern = Pattern.compile(regex);
System.out.println(pattern.matcher("1").matches());
System.out.println(pattern.matcher("12345").matches());
System.out.println(pattern.matcher("123456789").matches());

Ответ 3

Еще одно решение, которое еще не было опубликовано:

String regex = "\\p{Digit}+"; // uses POSIX character class

Ответ 4

Long.parseLong(data)

и исключение catch, оно обрабатывает знак минус.

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

Ответ 5

Вы должны разрешить больше цифры (знак +), как в:

String regex = "[0-9]+"; 
String data = "23343453"; 
System.out.println(data.matches(regex));

Ответ 6

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

Я предлагаю просто проверить, является ли каждый символ цифрой, что можно эффективно выполнить с помощью ямбда-выражений Java 8:

boolean isNumeric = someString.chars().allMatch(x -> Character.isDigit(x));

Ответ 7

В соответствии с Oracle Java Documentation:

private static final Pattern NUMBER_PATTERN = Pattern.compile(
        "[\\x00-\\x20]*[+-]?(NaN|Infinity|((((\\p{Digit}+)(\\.)?((\\p{Digit}+)?)" +
        "([eE][+-]?(\\p{Digit}+))?)|(\\.((\\p{Digit}+))([eE][+-]?(\\p{Digit}+))?)|" +
        "(((0[xX](\\p{XDigit}+)(\\.)?)|(0[xX](\\p{XDigit}+)?(\\.)(\\p{XDigit}+)))" +
        "[pP][+-]?(\\p{Digit}+)))[fFdD]?))[\\x00-\\x20]*");
boolean isNumber(String s){
return NUMBER_PATTERN.matcher(s).matches()
}

Ответ 8

Мы можем использовать либо Pattern.compile("[0-9]+.[0-9]+"), либо Pattern.compile("\\d+.\\d+"). Они имеют одинаковый смысл.

шаблон [0-9] означает цифру. То же, что и '\ d'. "+" означает, что он появляется больше раз. '' для integer или float.

Попробуйте выполнить следующий код:

import java.util.regex.Pattern;

    public class PatternSample {

        public boolean containNumbersOnly(String source){
            boolean result = false;
            Pattern pattern = Pattern.compile("[0-9]+.[0-9]+"); //correct pattern for both float and integer.
            pattern = Pattern.compile("\\d+.\\d+"); //correct pattern for both float and integer.

            result = pattern.matcher(source).matches();
            if(result){
                System.out.println("\"" + source + "\""  + " is a number");
            }else
                System.out.println("\"" + source + "\""  + " is a String");
            return result;
        }

        public static void main(String[] args){
            PatternSample obj = new PatternSample();
            obj.containNumbersOnly("123456.a");
            obj.containNumbersOnly("123456 ");
            obj.containNumbersOnly("123456");
            obj.containNumbersOnly("0123456.0");
            obj.containNumbersOnly("0123456a.0");
        }

    }

Вывод:

"123456.a" is a String
"123456 " is a String
"123456" is a number
"0123456.0" is a number
"0123456a.0" is a String

Ответ 9

Попробуйте эту часть кода:

void containsOnlyNumbers(String str)
{
    try {
        Integer num = Integer.valueOf(str);
        System.out.println("is a number");
    } catch (NumberFormatException e) {
        // TODO: handle exception
        System.out.println("is not a number");
    }

}