java 使用 Scanner 的 nextLine() 和 hasNextLine() 方法的问题
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/3652586/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Problem using the nextLine() and hasNextLine() methods of Scanner
提问by Harish
I have a log file containing the following data:
我有一个包含以下数据的日志文件:
Shortest path(2)::RV3280-RV0973C-RV2888C
Shortest path(1)::RV3280-RV2502C
Shortest path(2)::RV3280-RV2501C-RV1263
Shortest path(2)::RV2363-Rv3285-RV3280
最短路径(2)::RV3280-RV0973C-RV2888C
最短路径(1)::RV3280-RV2502C
最短路径(2)::RV3280-RV2501C-RV1263
最短路径(2)::RV2363-Rv3285-RV3280
From each line, i require the number within the brackets, name of the first protein (RV3280 in the first line) and the name of the last protein (RV2888C in the first line).
在每一行中,我需要括号内的数字、第一个蛋白质的名称(第一行中的 RV3280)和最后一个蛋白质的名称(第一行中的 RV2888C)。
I have written a code for this using the Scanner
object.
我已经使用Scanner
对象为此编写了代码。
try{
Scanner s = new Scanner(new File(args[0]));
while (s.hasNextLine()) {
s.findInLine("Shortest path\((\d+)\)::(\w+).*-(\w+)"); // at each line, look for this pattern
MatchResult result = s.match(); // results from
for (int i=1; i<=result.groupCount(); i++) {
System.out.println(result.group(i));
}
s.nextLine(); // line no. 29
}
s.close();
}
catch (FileNotFoundException e) {
System.out.print("cannot find file");
}
I get the desired results but i also get an error message. The output i get for the above input file is:
我得到了想要的结果,但我也收到了一条错误消息。我为上述输入文件得到的输出是:
Exception in thread "main" java.util.NoSuchElementException: No line found
at java.util.Scanner.nextLine(Scanner.java:1516)
at nearnessindex.Main.main(Main.java:29)
2
RV3280
RV2888C
1
RV3280
RV2502C
2
RV3280
RV1263
2
RV2363
RV3280
Java Result: 1
BUILD SUCCESSFUL (total time: 1 second)
Why does this error occur and how can correct it?
为什么会出现此错误,如何纠正?
采纳答案by Key
Your input data probably doesn't end with a line separator which would cause this. Calls to findInLine
moves the Scanner past the matching pattern and if you are at the end of the input data when calling nextLine
it will throw the NoSuchElementException
您的输入数据可能不会以行分隔符结尾,这会导致这种情况。调用findInLine
将 Scanner 移过匹配模式,如果您在调用nextLine
它时处于输入数据的末尾,则会抛出NoSuchElementException
A easy fix without re-arranging the code to much would be to end the while loop with:
一个简单的解决方法是在不重新安排代码的情况下结束 while 循环:
if (s.hasNextLine()) {
s.nextLine();
}
回答by atamanroman
public static void main(String[] args) {
Scanner s = new Scanner("Shortest path(2)::RV3280-RV0973C-RV2888C"
+ "\nShortest path(1)::RV3280-RV2502C"
+ "\nShortest path(2)::RV3280-RV2501C-RV1263"
+ "\nShortest path(2)::RV2363-Rv3285-RV3280");
while (s.hasNextLine()) {
s.findInLine("Shortest path\((\d+)\)::(\w+).*-(\w+)"); // at each line, look for this pattern
MatchResult result = s.match(); // results from
for (int i = 1; i <= result.groupCount(); i++) {
System.out.println(result.group(i));
}
s.nextLine(); // line no. 29
}
s.close();
}
}
run:
2
RV3280
RV2888C
1
RV3280
RV2502C
2
RV3280
RV1263
2
RV2363
RV3280
BUILD SUCCESSFUL (total time: 0 seconds)
This works well for me, maybe you have some weird characters or empty lines in your file?
这对我很有效,也许您的文件中有一些奇怪的字符或空行?
2 empty lines at the end give me that: Exception in thread "main" java.lang.IllegalStateException: No match result available
最后的 2 个空行给了我:线程“main”中的异常 java.lang.IllegalStateException: No match result available
If your input file is that strictly formatted, you can do something like that, which is way easier because you can get rid of that nasty regex ;)
如果您的输入文件格式严格,您可以做类似的事情,这更容易,因为您可以摆脱那些讨厌的正则表达式;)
String[] lines = new String[]{"Shortest path(2)::RV3280-RV0973C-RV2888C", "Shortest path(1)::RV3280-RV2502C", "Shortest path(2)::RV3280-RV2501C-RV1263", "Shortest path(2)::RV2363-Rv3285-RV3280", "\n", "\n"};
final int positionOfIndex = 14;
final int startPositionOfProteins = 18;
for (String line : lines) {
if (!line.trim().isEmpty()) {
System.out.print(line.charAt(positionOfIndex) + ": ");
String[] proteins = line.substring(startPositionOfProteins).split("-");
System.out.println(proteins[0] + " " + proteins[proteins.size() -1]);
}
}