Java中如何解析包含姓名与数字的字符串,提取姓名并计算数字平均值?
解析姓名与数字并计算平均值的实现方案
嘿,你的思路其实已经抓对核心了!用Scanner来处理这种空格分隔的字符串完全没问题——这就是Java里处理这类文本解析的常用工具,不用纠结是不是“输入字符串流”,Scanner本质上就是帮你把字符串拆分成一个个独立标记的帮手,刚好适配你的需求。
先给你的代码点个赞,逻辑已经很完整了,不过咱们可以再优化下细节,同时把步骤拆解清楚:
你的代码逻辑拆解
你写的代码其实已经完成了核心功能,我帮你理清楚每一步在做什么:
- 用
Scanner scnr = new Scanner(text);把输入字符串封装成可逐段读取的对象,Scanner会自动按空格分割内容。 - 循环判断
scnr.hasNext(),只要还有未读取的标记就继续:- 如果当前标记是整数(
scnr.hasNextInt()),就把它加入总和、计数加1。 - 否则就把它拼接到姓名字符串里,用
sep变量控制空格,避免姓名开头出现多余空格,这个细节处理得很到位!
- 如果当前标记是整数(
- 最后把姓名和计算出的平均值拼接成指定格式返回。
优化后的代码
这里给你调整了几个点,让代码更健壮、高效:
public static String parseNameNumbers(String text) { Scanner scnr = new Scanner(text); int numSum = 0; int countNum = 0; // 用StringBuilder代替String拼接,避免多次创建临时字符串,效率更高 StringBuilder nameBuilder = new StringBuilder(); String sep = ""; while(scnr.hasNext()) { if(scnr.hasNextInt()) { numSum += scnr.nextInt(); countNum++; } else { nameBuilder.append(sep).append(scnr.next()); sep = " "; } } // 处理没有数字的边界情况,避免除以0抛出异常 if(countNum == 0) { return nameBuilder.toString() + ": No numbers found"; } // 用浮点除法计算更精确的平均值,避免整数除法截断小数 double average = (double) numSum / countNum; // 如果需要只保留整数,就用(int)average;要保留小数可以用String.format控制格式 return nameBuilder.toString() + ": " + (int) average; }
关键优化说明
- 用
StringBuilder替代String拼接:Java里String是不可变对象,每次拼接都会生成新的String实例,当姓名很长时会浪费内存,StringBuilder是可变的,拼接效率更高。 - 处理无数字的边界情况:如果输入字符串里没有数字,原来的代码会触发
ArithmeticException(除以0错误),这里增加判断后会返回友好提示。 - 浮点除法计算平均值:原来的整数除法会直接截断小数部分(比如总和7、计数3的话,7/3会得到2而不是2.333),改成
(double)numSum / countNum可以得到更准确的结果,如果你需要保留整数,再强制转成int即可。
完整实施步骤总结
- 封装输入字符串:用
Scanner把目标字符串转换成可逐标记读取的对象。 - 初始化变量:准备求和变量、计数变量、用于构建姓名的
StringBuilder,以及控制空格的分隔符。 - 逐标记解析:循环读取每个标记,判断是数字就累加计数,是非数字就拼接到姓名中。
- 处理边界情况:检查是否有数字,避免除以0的错误。
- 计算并格式化结果:计算平均值,按指定格式拼接姓名和平均值后返回。
内容的提问来源于stack exchange,提问作者anony1414




