Php 将CSV数据导入MySQL
考虑以下来自“NASDAQ.CSV”的CSV数据片段 我正在尝试将符号、扇区和行业导入到一个MySQL表中,其中包含相应的字段:Php 将CSV数据导入MySQL,php,csv,import,Php,Csv,Import,考虑以下来自“NASDAQ.CSV”的CSV数据片段 我正在尝试将符号、扇区和行业导入到一个MySQL表中,其中包含相应的字段: $path = "NASDAQ.csv"; $row = 1; if (($handle = fopen($path, "r")) !== FALSE) { while (($data = fgetcsv($handle, 1000, ",")) !== FALSE) { $row++; $entries[] = $data ; } fcl
$path = "NASDAQ.csv";
$row = 1;
if (($handle = fopen($path, "r")) !== FALSE) {
while (($data = fgetcsv($handle, 1000, ",")) !== FALSE) {
$row++;
$entries[] = $data ;
}
fclose($handle);
}
foreach ($entries as $line) {
db_query("
INSERT INTO us_stocks (symbol, name, sector, industry)
VALUES ('%s', '%s', '%s', '%s', '%s')",
$line[0], $line[1], $line[6], $line[7]
);
}
然而,结果并不是我所期望的。在数据库中,只有符号字段被填充,甚至不正确:
symbol name sector industry
----------------------------------
Symbol,"Na
FLWS,"1-80
FCTY,"1st
FCCY,"1st
我做错了什么
[编辑]
如果我打印r($entries),输出如下
Array (
[0] => Array(
[0] => Symbol,"Name","LastSale","MarketCap","ADR TSO","IPOyear","Sector","industry","Summary Quote",;;
)
[1] => Array(
[0] => FLWS,"1-800 FLOWERS.COM, Inc.","2.9","81745200","n/a","1999","Consumer Services","Other Specialty Stores","http://www.nasdaq.com/symbol/flws",;;
)
[2] => Array(
[0] => FCTY,"1st Century Bancshares, Inc","4","36172000","n/a","n/a","Finance","Major Banks","http://www.nasdaq.com/symbol/fcty",;;
)
)
[编辑二]
我已经按照建议删除了CSV的第一行。我现在有了一个非常快速和肮脏的方式,几乎实现了我想要的。基本上,只要公司名称中有“.Inc”,事情就会搞砸。所以我只是把它“粘”到上面的名字上:$data[1]=$data[1]$资料[2]:
$path = "NASDAQ.csv";
$row = 1;
if (($handle = fopen($path, "r")) !== FALSE) {
while (($data = fgetcsv($handle, 1000, ";;")) !== FALSE) {
if ($row < 100) {
$row++;
$data = explode(',', $data[0]);
if (substr($data[2], 0, 1) == ' ') {
$data[1] = $data[1] . $data[2];
unset($data[2]);
}
$entries[] = $data ;
}
}
fclose($handle);
}
最后一个问题:我不知道如何重新编号。所以3到2,4到3,等等,这样输出看起来像:
[0] => Array
(
[0] => FLWS
[1] => "1-800 FLOWERS.COM Inc."
[2] => "2.9"
[3] => "81745200"
[4] => "n/a"
[5] => "1999"
[6] => "Consumer Services"
[7] => "Other Specialty Stores"
[8] => "http://www.nasdaq.com/symbol/flws"
[9] =>
)
任何帮助都将不胜感激 正如Crontab所说,这可能是引号的问题。尝试:
foreach ($entries as $line) {
// Escape (see mysql_real_escape_string too) and remove double quotes
foreach ($line as $k => $v) $line[$k] = mysql_escape_string(trim($v, '"'));
// Rebuild array
$line = array_values($line);
db_query("
INSERT INTO us_stocks (symbol, name, sector, industry)
VALUES ('%s', '%s', '%s', '%s', '%s')",
$line[0], $line[1], $line[6], $line[7]
);
}
PS:我不知道您是否已经在
db_query()
中转义了字符串,正如Crontab所说,这可能是引号的问题。尝试:
foreach ($entries as $line) {
// Escape (see mysql_real_escape_string too) and remove double quotes
foreach ($line as $k => $v) $line[$k] = mysql_escape_string(trim($v, '"'));
// Rebuild array
$line = array_values($line);
db_query("
INSERT INTO us_stocks (symbol, name, sector, industry)
VALUES ('%s', '%s', '%s', '%s', '%s')",
$line[0], $line[1], $line[6], $line[7]
);
}
PS:我不知道您是否已经在db_query()
中转义了字符串,我想说数据不是“真正的”CSV
“FLWS”、“1-800 FLOWERS.COM有限公司”、“2.9”,
应该是:
“FLWS”、“1-800 FLOWERS.COM,INC.”和“2.9”-引号应将各个字段用逗号分隔。通常数字字段不进行包装
根据您加载数据的方式,数据中的逗号可能会混淆数据。(即FLOWERS.COM,INC.)
顺便说一句,如果它真的是CSV,请看:我想说,数据不是“真正的”CSV
“FLWS”、“1-800 FLOWERS.COM有限公司”、“2.9”,
应该是:
“FLWS”、“1-800 FLOWERS.COM,INC.”和“2.9”-引号应将各个字段用逗号分隔。通常数字字段不进行包装
根据您加载数据的方式,数据中的逗号可能会混淆数据。(即FLOWERS.COM,INC.)
顺便说一句,如果它真的是CSV,请看:我猜它与CSV文件中使用的双引号有关。
fgetcsv()
($enclosure
)的第四个参数可以设置为“\”“
查看是否是这种情况。我猜这与CSV文件中使用的双引号有关。fgetcsv()
($enclosure
)的第四个参数可以设置为“\”
看看情况是否如此。好吧,这肯定不是我见过的最好的csv文件……但它是nasday.com上的可用文件,我找不到任何其他来源来导入所有美国股票的股票代码(我有其他csv,如美国运通、纽约证券交易所,来自同一个网站)。我不能全部删除吗“和‘来自所有字段?’第1行必须有输入错误,因为引号外的符号和名称之间没有分隔符。我只需将所有的”“替换为“(将2 x引号更改为1 x引号)使用加载数据填充跳过第1行,并指定要加载的列..我保证如果使用加载数据填充,插入速度会非常快。可能吧,但现在,我认为在php中对某些东西进行组合对我来说更快…顺便说一句:)如果有时间,请看一下我的最后一个问题-如何重新对键编号。有一个加载数据填充的例子-仅供参考。在另一个问题上,请看数组值和数组键-我确定它们是您想要的。非常快而且脏,我使用$data=array\u merge(array(),$data);来重新索引。问题已解决。谢谢:)嗯,这肯定不是我见过的最好的csv文件…但它是nasday.com上提供的,我找不到任何其他来源来导入所有美国股票的股票代码(我有其他csv,如美国运通、纽约证券交易所,来自同一个网站)。我能不能从所有字段中删除“所有”和“所有字段”?第一行必须有一个打字错误,因为引号外的符号和名称之间没有分隔符。我只需要将所有的“”替换为“(将tr2 x引号更改为1 x引号)使用load data Infle跳过第1行,指定要加载的列。我保证如果使用load data Infle,插入速度会非常快。可能,但现在,我认为在php中对某些东西进行黑客攻击对我来说速度更快…几乎达到了,顺便说一句:)请看一下我的最后一个问题-如何对键重新编号-如果你愿意的话有时间。有一个加载数据填充的例子-仅供参考。在另一个问题上,看看数组值和数组键-我确信它们就是你想要的。非常快而且脏,我使用了$data=array\u merge(array(),$data);重新编制索引。问题已解决。谢谢:)我已经这样做了。但是,它不起作用。您的代码也不起作用。由于双重转义,它现在只读取FLWS、\“1-8等。也许使用regex删除每个$data行中的所有单引号和双引号会更好?trim($v,“”)
删除字符串开头和结尾的单引号或多引号。因此,恐怕是fgetcsv()
无法正确解析该CSV。在查询之前,在没有我的代码的情况下,您是否尝试过查看print\r($line)
?字段是否正确拆分?@Reveller好的,现在您明白了!您只需使用trim($v,“”)消除双引号即可。
正如我已经向您展示的那样。然后,要消除索引跳转并重新编码数组,只需array\u values()
。查看我的更新答案:)我已经这样做了。但是,它不起作用。你的代码也不是。由于双转义,它现在只读取FLWS、\“1-8等。也许最好只使用正则表达式从每个$data行中删除所有单引号和双引号?trim($v,”)
从字符串的开头和结尾删除单引号或多个双引号。因此,恐怕是fgetcsv()
无法正确解析该CSV。在查询之前,在没有我的代码的情况下,您是否尝试过查看打印($line)的输出?是spli吗
foreach ($entries as $line) {
// Escape (see mysql_real_escape_string too) and remove double quotes
foreach ($line as $k => $v) $line[$k] = mysql_escape_string(trim($v, '"'));
// Rebuild array
$line = array_values($line);
db_query("
INSERT INTO us_stocks (symbol, name, sector, industry)
VALUES ('%s', '%s', '%s', '%s', '%s')",
$line[0], $line[1], $line[6], $line[7]
);
}