CSV 到 JSON 与 PHP?
Posted
技术标签:
【中文标题】CSV 到 JSON 与 PHP?【英文标题】:CSV to JSON with PHP? 【发布时间】:2011-06-16 06:13:32 【问题描述】:我需要在服务器上使用 php 将 CSV 文件转换为 JSON。我正在使用这个有效的脚本:
function csvToJSON($csv)
$rows = explode("\n", $csv);
$i = 0;
$len = count($rows);
$json = "\n" . ' "data" : [';
foreach ($rows as $row)
$cols = explode(',', $row);
$json .= "\n \n";
$json .= ' "var0" : "' . $cols[0] . "\",\n";
$json .= ' "var1" : "' . $cols[1] . "\",\n";
$json .= ' "var2" : "' . $cols[2] . "\",\n";
$json .= ' "var3" : "' . $cols[3] . "\",\n";
$json .= ' "var4" : "' . $cols[4] . "\",\n";
$json .= ' "var5" : "' . $cols[5] . "\",\n";
$json .= ' "var6" : "' . $cols[6] . "\",\n";
$json .= ' "var7" : "' . $cols[7] . "\",\n";
$json .= ' "var8" : "' . $cols[8] . "\",\n";
$json .= ' "var9" : "' . $cols[9] . "\",\n";
$json .= ' "var10" : "' . $cols[10] . '"';
$json .= "\n ";
if ($i !== $len - 1)
$json .= ',';
$i++;
$json .= "\n ]\n";
return $json;
$json = csvToJSON($csv);
$json = preg_replace('/[ \n]/', '', $json);
header('Content-Type: text/plain');
header('Cache-Control: no-cache');
echo $json;
$csv
变量是一个返回 CSV 内容的 cURL 请求产生的字符串。
我确信这不是最有效的 PHP 代码,因为我是初学者,我对 PHP 的了解很少。 有没有更好、更有效的方法来使用 PHP 将 CSV 转换为 JSON?
提前致谢。
注意。我知道我要添加空格然后删除它,我这样做是为了可以选择通过删除行 $json = preg_replace('/[ \n]/', '', $json);
来返回“可读”JSON 以用于测试目的.
编辑。感谢您的回复,基于他们的新代码如下:
function csvToJson($csv)
$rows = explode("\n", trim($csv));
$csvarr = array_map(function ($row)
$keys = array('var0','var1','var2','var3','var4','var5','var6','var7','var8','var9','var10');
return array_combine($keys, str_getcsv($row));
, $rows);
$json = json_encode($csvarr);
return $json;
$json = csvToJson($csv);
header('Content-Type: application/json');
header('Cache-Control: no-cache');
echo $json;
【问题讨论】:
【参考方案1】:这里有 json_encode() 函数,您应该使用它而不是自己构建 JSON 输出。还有一个函数 str_getcsv() 用于解析 CSV:
$array = array_map("str_getcsv", explode("\n", $csv));
print json_encode($array);
但是,如果您希望 JSON 输出包含命名字段,则必须调整 $array。
【讨论】:
非常感谢,这是一个非常干净的解决方案,我根据您的回答使用我现在使用的代码编辑了我的帖子,并添加了 array_combine 以输出带有属性名称的 JSON。 +1 真是太棒了。不知道str_getcsv
。如果您还知道如何防止破坏多行单元格...:D【参考方案2】:
我修改了问题中的答案,将 CSV 的第一行用作数组键。这样做的好处是不必对函数中的键进行硬编码,使其适用于具有列标题和任意数量列的任何 CSV。
这是我的修改版本:
function csvToJson($csv)
$rows = explode("\n", trim($csv));
$data = array_slice($rows, 1);
$keys = array_fill(0, count($data), $rows[0]);
$json = array_map(function ($row, $key)
return array_combine(str_getcsv($key), str_getcsv($row));
, $data, $keys);
return json_encode($json);
【讨论】:
【参考方案3】:一些提示...
如果您为fopen()
和包装器启用了URL 打开,您可以使用fgetscsv()
。
您可以构建一个 CSV 数组,然后使用 PHP 的原生 json_encode()
进行转换。
JSON 的正确 MIME 类型是 application/json
。
【讨论】:
谢谢,现在我正在使用 json_encode() 并更正了 mime 类型。【参考方案4】:这些答案都不适用于多行单元格,因为它们都假设一行以“\n”结尾。内置的 fgetcsv
函数理解多行单元格包含在 " 中,因此它不会遇到相同的问题。下面的代码不是依靠 '\n' 来查找 csv 的每一行,而是让 fgetcsv
逐行行并准备我们的输出。
function csv_to_json($file)
$columns = fgetcsv($file); // first lets get the keys.
$output = array(); // we will build out an array of arrays here.
while(!feof($file)) // until we get to the end of file, we'll pull in a new line
$line = fgetcsv($file); // gets the next line
$lineObject = array(); // we build out each line with our $columns keys
foreach($columns as $key => $value)
$lineObject[$value] = $line[$key];
array_push($output, $lineObject);
return json_encode($output); // encode it as json before sending it back
【讨论】:
【参考方案5】:您可以通过删除所有空格和\n 来减少开销。但这在你的笔记里。
您可以通过跳过 preg_replace 并传递一个可以打开和关闭它的布尔值来提高性能。
除此之外,你的 var[1-10] 的变量展开实际上是好的,只要总是有十个变量。
explode 和 foreach 方法都很好。
【讨论】:
我最终使用更清洁的解决方案删除了空格,谢谢。【参考方案6】:我建议使用Coseva(一个 csv 解析库)并使用内置的 toJSON() 方法。
<?php
// load
require('../src/CSV.php');
// read
$csv = new Coseva\CSV('path/to/my_csv.csv');
// parse
$csv->parse();
// disco
echo $csv->toJSON();
【讨论】:
以上是关于CSV 到 JSON 与 PHP?的主要内容,如果未能解决你的问题,请参考以下文章