
本文介绍如何用 php 正确读取含城市名与人口数据的文本文件,构建以城市为键、人口为值的关联数组,按人口降序排序,并以 html 表格格式规范输出结果。
本文介绍如何用 php 正确读取含城市名与人口数据的文本文件,构建以城市为键、人口为值的关联数组,按人口降序排序,并以 html 表格格式规范输出结果。
实现该功能的关键在于:准确解析字段分隔符、正确构建关联数组、使用合适的排序函数、避免索引越界错误。原始代码存在多个问题:误将空格作为唯一分隔符(导致城市名含空格时解析失败)、错误调用 explode('.', $data[$index][0])(数据中并无点号)、usort() 后仍试图访问 $item[0]/$item[1]/$item[2](但此时数组结构已非二维索引数组,且未清理换行符)。
实际上,示例数据采用的是制表符(\t)或连续空格对齐,但更可靠的方式是使用 preg_split() 按空白字符分割并过滤空元素;不过鉴于数据格式规整,推荐先用 trim() 清理行尾换行符,再用 preg_split('/\s+/', $row, 2) 精确切分为两部分(城市名 + 人口),确保人口值不被多余空格污染。
以下是优化后的完整可运行代码:
<?php // 1. 安全打开文件并检查是否成功
$fileHandler = fopen("Info_array.txt", "r");
if (!$fileHandler) {
die("Error: Unable to open file Info_array.txt");
}
$data = [];
// 2. 逐行读取并解析
while (($row = fgets($fileHandler)) !== false) {
$row = trim($row); // 去除换行符和首尾空格
if (empty($row)) continue; // 跳过空行
// 按一个或多个空白字符分割,仅分割为两部分:城市名 + 人口
$parts = preg_split('/\s+/', $row, 2);
if (count($parts) === 2) {
[$city, $population] = $parts;
$data[trim($city)] = (int)trim($population); // 键为城市(去空格),值为整型人口
}
}
fclose($fileHandler);
// 3. 按人口值降序排序(arsort 保持键值关联)
arsort($data);
?>
| City | Population |
|---|---|
| = htmlspecialchars($city) ?> | = number_format($population) ?> |
✅ 关键改进说明:
- 使用 preg_split('/\s+/', $row, 2) 确保只分割一次,避免城市名中含空格(如 “New York”)被错误截断;
- 显式 trim() 城市名与人口值,消除对齐空格干扰;
- 将人口转为 (int) 类型,便于数值排序与后续计算;
- 使用 arsort() 直接按值降序排列并保留键名,语义清晰、无需自定义比较函数;
- 输出前调用 htmlspecialchars() 防止 XSS(若文件内容不可信);
- number_format() 提升人口数字可读性(如 39105000 → 39,105,000);
- 添加基础 CSS 样式提升表格可读性。
⚠️ 注意事项:
- 确保 Info_array.txt 文件编码为 UTF-8(无 BOM),否则中文城市名可能乱码;
- 若文件路径不在当前脚本同目录,请使用绝对路径或 __DIR__ . '/Info_array.txt';
- 生产环境建议增加异常处理(如 try/catch 包裹文件操作);
- 对于超大文件,可考虑使用 file() 函数一次性读入后遍历,或改用 SplFileObject 流式处理。
该方案简洁、健壮、符合 PHP 最佳实践,能稳定处理题目所给数据及常见变体格式。
php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











