如何修正正则表达式以修复含换行的CSV文件(PHP)
修复含换行符的CSV文件(PHP实现)
问题描述
正常CSV格式如下:
id, text field1, text field2 1,some text,another text 2,some text,another text 3,some text,another text
但text field1中偶尔会包含换行符,导致CSV结构损坏:
id, text field1, text field2 1,some text,another text 2,some text,another text 3,some text,another text
逐行读取或按换行拆分时会得到无效记录。原修复代码在遇到换行后是数字(如日期1999-06-21)时失效:
<?php $c= file_get_contents($myFile); $c= preg_replace( '/\n([^0-9])/is', "\n~~$1", $c ); $c= str_replace( "\n~~", " ", $c ); ?>
解决方案
正则优化方案
换个思路:匹配那些不是以数字+逗号开头的行内换行,因为正常数据行都是以数字,起始的。修改后的代码更精准高效:
<?php $content = file_get_contents($myFile); // 负向前瞻断言:换行后不能紧跟数字+逗号,直接替换为空格 $content = preg_replace('/\n(?!\d+,)/is', ' ', $content); file_put_contents($fixedFile, $content); ?>
非正则高效方案(适配10万+条记录)
正则处理超大文件可能占用过多内存,推荐逐行读取+状态判断的方式,内存占用极低:
<?php $input = fopen($myFile, 'r'); $output = fopen($fixedFile, 'w'); // 写入表头 $header = fgets($input); fwrite($output, $header); $currentRecord = ''; while (($line = fgets($input)) !== false) { // 判断当前行是否是新记录起始(以数字开头) if (preg_match('/^\d+,/', $line)) { // 写入上一条完整记录 if (!empty($currentRecord)) { fwrite($output, trim($currentRecord) . "\n"); } $currentRecord = $line; } else { // 将换行内容追加到当前记录,替换换行为空格 $currentRecord .= ' ' . trim($line); } } // 写入最后一条记录 if (!empty($currentRecord)) { fwrite($output, trim($currentRecord) . "\n"); } fclose($input); fclose($output); ?>
内容的提问来源于stack exchange,提问作者John
相关产品推荐
相关产品推荐

