发布于2026-07-11 阅读(0)
扫一扫,手机访问
在日常开发中,跟字符串里的数据打交道是家常便饭,尤其是要从一串格式固定的文本里把数字一个个揪出来。这事儿,Ja va 的 ja va.util.Scanner 干得漂亮,但也确实有几个容易栽跟头的细节。下面梳理的几个要点,都是从实战里趟出来的经验,看懂这些,基本能避免它八成的坑。

最直接的用法,就是直接把待解析的字符串塞给 Scanner 的构造器。比如 new Scanner("12 34 56"),干净利落。别想着先造个空 Scanner,再折腾什么 nextLine() 往里填数据,那条路走不通。Scanner 的输入源在它出生那一刻就绑死了,后面想换?门都没有。常有新手写成 Scanner sc = new Scanner(System.in); sc = new Scanner("12 34 56");,这就把第一个对象扔了,逻辑上也是一笔糊涂账。
正确的做法就是:你想要解析哪个字符串,就直接把它当构造参数传进去。之后,所有 next* 方法都会按分隔符(默认是空白字符,像空格、tab这些)从这个字符串里一个一个往外取数据块,也就是“token”。
这是个老生常谈,但也是最容易被忽视的。二话不说就 nextInt(),就像闭着眼睛过马路。数据格式稍微有点意外,比如字符串末尾多了个空格,或者中间混进来一个字母,程序啪的一下就摔给你一个 NoSuchElementException 或者 InputMismatchException。它不会跳过错误,只会罢工。
安全驾驶的关键一步,是带上 hasNextInt() 这个“哨兵”:
Scanner sc = new Scanner("12 abc 34 56");
while (sc.hasNext()) {
if (sc.hasNextInt()) {
System.out.println(sc.nextInt()); // 输出 12, 34, 56
} else {
sc.next(); // 跳过非整数 token,比如 "abc"
}
}
这等于给了解析流程一个“预检”过程,只处理能吃的数字,吃不下的就绕过去,程序健壮性一下子就上来了。
默认的空白符分隔虽然方便,但不是万能的。比如你拿到一串 "12,34,56",直接用默认设置去读,nextInt() 就会报错,因为它把整个 "12,34,56" 当成了一个整体,而这个东西显然不是一个合法的整数。这属于典型的“牛头不对马嘴”。
解决方案就是显式告诉 Scanner:“喂,哥们,我们的分隔符是逗号。” 立刻调用 useDelimiter() 方法就行:
sc.useDelimiter(",") —— 只认字面上的逗号。sc.useDelimiter("[,\s]+") —— 更鲁棒的做法,同时支持逗号和任意数量的空白字符。这里需要特别注意正则表达式的写法,Ja va 字符串里的反斜杠必须双写,"\s" 才能正确表示空白字符这个类。一旦设好了,nextInt() 就能准确地把每个数字从字符串里“切”出来。
对于基于字符串的 Scanner,调用 close() 更多是一种编程习惯,而不是必需品。因为它背后没有打开文件、网络连接这类需要释放的系统资源。但养成这个习惯没坏处,万一你的代码哪天升级成从文件读取数据(比如 new Scanner(new File("data.txt"))),就不会因为忘记 close() 而埋下资源泄漏的隐患。
我个人更推荐用 try-with-resources 结构,让 JVM 替你把关:
try (Scanner sc = new Scanner("12 34 56")) {
while (sc.hasNextInt()) {
System.out.println(sc.nextInt());
}
} // 自动 close
最后再多啰嗦几句,实战中最容易让人吃瘪的几个小地方:正则格式写错(比如漏了方括号或反斜杠)、误以为 next() 能跳过一整行(它只跳过当前一个 token)、以及没处理混合类型输入时的异常。这些细节每一个都可能让代码运行到一半就卡住。把这些点都盯住了,用 Scanner 解析字符串这件事,基本也就稳了。
售后无忧
立即购买>office旗舰店
售后无忧
立即购买>office旗舰店
售后无忧
立即购买>office旗舰店
售后无忧
立即购买>office旗舰店
正版软件
正版软件
正版软件
正版软件
正版软件
1
2
3
7
8