Je veux obtenir la valeur de l'entrée dans le scanner sans l'avancer. Actuellement, j'utilise l'entrée de mes scanners comme System.in
.
final var sc = new Scanner(System.in);
Je connais les hasNext
méthodes sur le scanner, et elles sont actuellement mon meilleur / seul moyen de vérifier son entrée sans l'avancer.
Voici comment j'assure une entrée intégrale positive sc
par exemple.
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();
}
Je veux étendre cette notion de vérification sc
de l'entrée de sans l'avancer pour obtenir réellement sc
l'entrée de sans l'avancer.
J'ai parcouru les détails de mise en œuvre de hasNext()
sur 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);
}
}
}
Il m'a semblé au moins que l'on peut obtenir les données du scanner à partir de la méthode getCompleteTokenInBuffer
, mais vraiment je ne comprends pas vraiment comment cela fonctionne. Je ne sais pas si cette méthode à elle seule obtient la valeur du scanner sans l'avancer, ou si elle l'avance, quelque chose d'autre le ramène à l'état dans lequel elle était avant l'entrée comme si elle n'avait pas avancé du tout, ou si l'obtient en combinaison avec autre chose, ou vraiment comment du tout.
J'ai joué avec l'invocation des méthodes privées Scanner
via l'API de réflexion de Java, pour essayer de renvoyer la sc
valeur d'entrée du jeton contenant des méthodes sans réellement faire avancer les méthodes (mais pour être honnête, je joue juste avec elle et je ne sais pas comment accomplir réellement ce que je veux faire).
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"
}
Remarque: La méthode ci-dessus n'attend pas une entrée avant d'obtenir la valeur de sc
's input et renvoie donc une valeur de null
.
Juste pour répéter, j'aimerais trouver un moyen de capturer et de renvoyer Scanner
la valeur d'entrée d' un objet en l'avançant réellement.
Ce que vous recherchez pourrait autrement être appelé une fonction peek.
Cette réponse sur un autre thread indique que vous pourriez être servi en créant une classe wrapper autour de Scanner qui implémente cette fonctionnalité, puisque la classe Scanner elle-même ne l'implémente pas.
Cet article est collecté sur Internet, veuillez indiquer la source lors de la réimpression.
En cas d'infraction, veuillez [email protected] Supprimer.
laisse moi dire quelques mots