fputcsv()是PHP导出CSV唯一推荐函数,自动转义逗号、换行、双引号;需用'w'模式打开文件、首行写入UTF-8 BOM(\xEF\xBB\xBF)防中文乱码、确保传入索引数组、流式处理大数据并正确设置HTTP头。

用 fputcsv() 写入 CSV 最稳妥
PHP 原生写 CSV,fputcsv() 是唯一推荐的函数。它自动处理字段中的逗号、换行、双引号等转义,避免手拼字符串导致 Excel 打开乱码或错列。
常见错误是直接 echo 或 fwrite() 拼接字符串,比如 "a,b,\"c\nd\",e" —— 这种写法在含中文、制表符、换行时极易崩,Excel 会把一行切两行,或者把引号当分隔符。
- 必须先用
fopen($filename, 'w')或'a'(追加)打开文件,不能用file_put_contents() - 每行数据传数组给
fputcsv(),不要提前 implode - 注意文件编码:如果含中文,确保文件以 UTF-8 无 BOM 保存,且在首行写入
\xEF\xBB\xBF(BOM)才能让 Excel 正确识别(Windows 上尤其关键)
写入带中文的 CSV 必须加 BOM 头
Windows 版 Excel 默认用 ANSI 解析 CSV,不加 BOM 就会把 UTF-8 中文显示成乱码。Mac 和 WPS 通常能自动识别,但生产环境不能赌。
实操就是写入前先输出三个字节:
立即学习“PHP免费学习笔记(深入)”;
从 CSV 数据集生成图数据库加载器和三元组映射。将表格 CSV 数据转换为图数据库可直接使用的节点、边和三元组。
if (empty($written_bom)) {
fwrite($fp, "\xEF\xBB\xBF");
$written_bom = true;
}
注意:\xEF\xBB\xBF 是硬编码,别用 chr() 拼;也别用 mb_convert_encoding() 转 BOM,它不生效。
- BOM 只需写一次,在第一行数据前
- 如果用
'a'模式追加写,要先判断文件是否为空,否则每次都会重复加 BOM - 用 Notepad++ 或 VS Code 查看文件实际开头是否有「EF BB BF」十六进制字节
fputcsv() 的 delimiter 和 enclosure 参数怎么设
默认用英文逗号 , 和双引号 ",够用。改参数只在特殊场景需要:
- 导出给某些老系统用,要求分隔符是分号
;(如部分欧洲 Excel 配置)→ 传第 3 个参数';' - 字段本身大量含双引号,想改用单引号包裹 → 第 4 个参数
"'",但注意 Excel 不认单引号为 enclosure,会导致解析失败,慎用 - 第 5 个参数
$escape_char默认是双引号,不建议改;改成反斜杠\后 Excel 打不开
示例:用分号分隔 + UTF-8 BOM
$fp = fopen('data.csv', 'w');
fwrite($fp, "\xEF\xBB\xBF");
fputcsv($fp, ['姓名', '城市', '备注'], ';');
fputcsv($fp, ['张三', '上海', "有\"引号"], ';');
fclose($fp);
追加写入和大文件性能要注意什么
小文件(fopen(..., 'a') 没问题;但大文件频繁打开关闭会慢,且并发写可能冲突。
- 写日志类 CSV,用
flock($fp, LOCK_EX)加锁,写完flock($fp, LOCK_UN) - 超 10 万行建议分批:每 5000 行
fflush($fp)一次,防内存积压 - 别用
file_get_contents() + str_replace() + file_put_contents()去“修改”CSV —— CSV 不是文本编辑器,没行列索引,这种操作必然破坏结构
最易被忽略的是:Windows 下用 'a' 模式打开文件后,即使文件不存在也会创建,但首次写入前不加 BOM,后续追加就永远缺头 —— 所以判断文件是否存在、是否为空、是否已有 BOM,这三步检查不能少。


















