Получить значение сканера, не продвигая его - Java
Я хочу получить значение ввода в сканере, не продвигая его.В настоящее время я использую вход для своих сканеров как System.in
.
final var sc = new Scanner(System.in);
Я знаю о hasNext
методах на сканере, и в настоящее время они - мой лучший / единственный способ проверить входные данные без его продвижения.
Вот как я могу обеспечить положительный результатнапример, интегральный ввод от sc
.
public static int getPositiveIntegerInput(Scanner sc) {
System.out.println("Please input a positive integer");
sc.useDelimiter("\n");
while (!sc.hasNextInt() || sc.hasNext(".*[^\\d].*")) {
System.out.println("Invalid input, please try again");
sc.nextLine();
}
return sc.nextInt();
}
Я хочу расширить это понятие проверки ввода sc
, не продвигая его до фактического получения ввода sc
без его продвижения.
Что я пытался до этого момента
Я прошел подробности реализации hasNext()
на Scanner
.
Реализация hasNext
:
public final class Scanner {
public boolean hasNext(Pattern pattern) {
ensureOpen();
if (pattern == null)
throw new NullPointerException();
hasNextPattern = null;
saveState();
modCount++;
while (true) {
if (getCompleteTokenInBuffer(pattern) != null) {
matchValid = true;
cacheResult();
return revertState(true);
}
if (needInput)
readInput();
else
return revertState(false);
}
}
}
Мне показалось, по крайней мере, что вход для сканера можно получить методом getCompleteTokenInBuffer
, но на самом деле я не очень понимаю, как он работает.Я не знаю, если этот метод сам по себе получает значение сканера, не продвигая его, или если он продвигает его, тогда что-то еще возвращает его обратно в состояние, в котором он находился до ввода, как если бы он вообще не продвигался, или если онполучает его в сочетании с чем-то другим, или вообще как.
Я пытался вызвать частные методы Scanner
через API отражения Java, чтобы попытаться фактически вернуть токен, содержащий sc
'входное значение без фактического продвижения методов (но, честно говоря, я просто играю с ним и не знаю, как на самом деле выполнить то, что я хочу сделать).
public static void main(String[] args) {
final var sc = new Scanner(System.in);
sc.useDelimiter("\n");
var str = "";
try {
Method method = Scanner.class.getDeclaredMethod("getCompleteTokenInBuffer", Pattern.class);
method.setAccessible(true);
str = (String) method.invoke(sc, Pattern.compile(".*"));
} catch (Exception e) {
System.out.println("Well, that didn't work!");
System.out.println("Exception: " + e);
}
System.out.println("getCompleteTokenInBuffer: " + str);
// Prints: "getCompleteTokenInBuffer: null"
}
Примечание: Приведенный выше метод не ожидает ввода, прежде чем получить значение sc
, и, следовательно, возвращает значение null
.
Цель:
Просто дляПовторюсь, я хотел бы найти способ захватить и вернуть Scanner
входное значение объекта с его фактическим продвижением.