fgetcsv() 无法识别 UTF-8 字符后的逗号?



我们有一个通过fgetcsv((读取的大型CSV文件:

$row = fgetcsv($this -> handle, null, ',', '"');

这一切都很好,直到其中一行看起来像这样:

The Parkway Dentist - We Can See U Now™,https://www.xxxx.com,together@xxxx.com,(817) 735-xxxx, ,4200,Benbrook,TX,76109,"Benbrook,TX 76109","Cosmetic Dentistry, Dentists, Endodontists, Implant Dentistry, Teeth Whitening Products & Services",, , , ,valid,the-parkway-dentist-we-can-see-u-now-465117871,32.69415,-97.41237,https://instagram.com/xxxx,https://www.facebook.com/xxxx, ,,

fgetcsv(( 解析如下:

Array
(
[0] => The Parkway Dentist - We Can See U Now鈩?https://www.xxxx.com
[1] => together@xxxx.com
[2] => (817) 735-xxxx
[3] =>
[4] => 4200
[5] => Benbrook
[6] => TX
[7] => 76109
[8] => Benbrook,TX 76109
[9] => Cosmetic Dentistry, Dentists, Endodontists, Implant Dentistry, Teeth Whitening Products & Services
[10] =>
[11] =>
[12] =>
[13] =>
[14] => valid
[15] => the-parkway-dentist-we-can-see-u-now-465117871
[16] => 32.69415
[17] => -97.41237
[18] => https://instagram.com/xxxx
[19] => https://www.facebook.com/xxxx
[20] =>
[21] =>
[22] =>
)

显然,fgetcsv(( 在第一个字段之后没有逗号分隔符,因此错误地将第一个和第二个字段粘合在一起,而它们应该作为 2 个不同的字段分开。

我们发现唯一不同的是逗号分隔符之前的 UTF-8 字符。

我们如何使fgetcsv(( 正确识别这里的情况?

更新

PHP 版本是 7.0.10。根据记事本++,CSV文件采用UTF-8-BOM编码。尝试了以下代码:

$line = fgets($this -> handle, 1048576);
print_r(mb_detect_encoding($line, 'UTF-8', true));

哪个输出:

UTF-8

所以看起来文件是 UTF-8 没有问题。

您可以在此处看到包含有问题的行的 CSV 文件:http://n3.datasn.io/utf8-problem.csv

我刚才用这段代码测试了这个文件:

$row = fgetcsv($this -> handle, null, ',', '"');
print_r($row);

它仍然输出第一个字段值为:

The Parkway Dentist - We Can See U Now鈩?https://www.xxxx.com

根据手册中的注释,"此函数会考虑区域设置。如果LC_CTYPE例如en_US。UTF-8,单字节编码的文件可能会被此函数错误地读取。

你有相反的问题。您正在尝试读取 UTF-8 文件,但区域设置使用不同的编码。您的"中文(简体(_China.936"LC_CTYPE使用代码页 936(简体中文(编码,因此除非您更改区域设置,否则fgetcsv无法打开 UTF-8 文件。

您可以按进程执行此操作,例如,如果系统上安装了en_US.UTF-8语言环境,setlocale(LC_ALL, 'en_US.UTF-8');— 但请阅读手册页上的警告,了解这会如何影响服务器上运行的其他脚本 — 或更改php.ini中的 intl.default-locale 设置。

最新更新