PHP电子表格读取CSV
我正在尝试用PHP电子表格库读取CSV文件 我成功地获取了数据,但是数组中的逗号分隔符弄错了PHP电子表格读取CSV,php,csv,spreadsheet,Php,Csv,Spreadsheet,我正在尝试用PHP电子表格库读取CSV文件 我成功地获取了数据,但是数组中的逗号分隔符弄错了 $reader = new \PhpOffice\PhpSpreadsheet\Reader\Csv(); $spreadsheet = $reader->load('File.csv'); $sheetData = $spreadsheet->getActiveSheet()->toArray(); echo '<pre>'; print_r($sheetData
$reader = new \PhpOffice\PhpSpreadsheet\Reader\Csv();
$spreadsheet = $reader->load('File.csv');
$sheetData = $spreadsheet->getActiveSheet()->toArray();
echo '<pre>';
print_r($sheetData);
而不是:
ini_set('auto_detect_line_endings',TRUE)
提前谢谢。您是否尝试过强制行尾保持一致?我以前遇到过这种情况,在解析CSV之前必须添加一个PHP ini设置:
<?php
use Exception;
use InvalidArgumentException;
use SplFileObject;
use NoRewindIterator;
class LargeFile {
const ERROR_UNABLE = 'ERROR: Unable to open file';
const ERROR_TYPE = 'ERROR: Type must be "ByLength", "ByLine", or "Csv"';
protected $file;
protected $allowed_types = [ 'ByLine', 'ByLength', 'Csv' ];
/**
* LargeFile constructor.
*
* @param $filename
* @param string $mode
*
* @throws Exception
*
* Populates $file with new SPL File object instance.
*/
public function __construct($filename, $mode = 'r') {
if (!file_exists($filename)) {
$message = __METHOD__ . ' : ' . self::ERROR_UNABLE . PHP_EOL;
$message .= strip_tags($filename) . PHP_EOL;
throw new Exception($message);
}
$this->file = new SplFileObject($filename, $mode);
}
/**
* @return \Generator|int
*
* References SplFileObject method to read the file one line
* at a time with fgets.
*
* Suitable for smaller text files like Csvs and / or
* include line feeds.
*/
protected function fileIteratorByLine() {
$count = 0;
while (!$this->file->eof()) {
yield $this->file->fgets();
$count++;
}
return $count;
}
/**
* @param $numBytes
*
* @return \Generator|int
*
* References SplFileObject method to read the file one line
* at a time with freads.
*
* Suitable for larger binary files.
*/
protected function fileIteratorByLength($numBytes) {
$count = 0;
while (!$this->file->eof()) {
yield $this->file->fread($numBytes);
$count++;
}
return $count;
}
protected function fileIteratorCsv() {
$count = 0;
while (!$this->file->eof()) {
yield $this->file->fgetcsv();
$count++;
}
return $count;
}
/**
* @param string $type
* @param null $numBytes
*
* @return NoRewindIterator
*/
public function getIterator($type = 'ByLine', $numBytes = null) {
if (!in_array($type, $this->allowed_types)) {
$message = __METHOD__ . ' : ' . self::ERROR_TYPE . PHP_EOL;
throw new InvalidArgumentException($message);
}
$iterator = 'fileIterator' . $type;
return new NoRewindIterator($this->$iterator($numBytes));
}
}
把它放在$reader前面
在评论中通过请求进行编辑
这里是我用于CSV的类,假设您至少有PHP5.5:
$largeFile = new LargeFile($file);
// tell it use the CSV iterator
$iterator = $largeFile->getIterator('Csv');
// start iterator and pull out header row as $rawHeaders
$rawHeaders = $iterator->current();
$headerIterator = new \ArrayIterator;
foreach ($rawHeaders as $header) {
$headerIterator->append(strtolower("`$header`"));
}
$headers = $headerIterator->getArrayCopy();
// move pointer to the data rows
$iterator->next();
// loop through each row
foreach( $iterator as $row ) {
// do stuff with each row
print_r($row);
}
嗨,JDev,我试过了,也遇到了同样的问题,我认为这与文件或库有关,因为如果我使用fgetcsv(),它会正确地分割到数组中。好吧,听起来你是对的,我不熟悉这个特定的库,它可能有特定的分隔符设置。我有一个用于所有CSV解析的库,如果您对JDev感兴趣的话,它更适合于较大的文件。当然,为什么不呢!谢谢,我以前使用过PHPExcel,并且可以很好地处理同一个文件,今天我转到了他们推荐的新库(电子表格),因为PHPExcel不推荐使用,所以我遇到了这个问题。我更新了我的原始答案。代码是我从一组迭代器/生成器类中提取的一个类,我将这些类用于各种事情。我得到第一行(CSV文件头),在$iterator->next()之后,它只循环遍历数据。getArrayCopy()与->toArray方法基本相同。当然可以。我决定用PHP内置的SPL/Generator类编写我自己的更基于OOP的类。将CSV结果作为迭代器输入可以节省大量内存,而不是每次都转储一个巨大的数组。因此“LargeFile”类名为:请提供csv文件
<?php
use Exception;
use InvalidArgumentException;
use SplFileObject;
use NoRewindIterator;
class LargeFile {
const ERROR_UNABLE = 'ERROR: Unable to open file';
const ERROR_TYPE = 'ERROR: Type must be "ByLength", "ByLine", or "Csv"';
protected $file;
protected $allowed_types = [ 'ByLine', 'ByLength', 'Csv' ];
/**
* LargeFile constructor.
*
* @param $filename
* @param string $mode
*
* @throws Exception
*
* Populates $file with new SPL File object instance.
*/
public function __construct($filename, $mode = 'r') {
if (!file_exists($filename)) {
$message = __METHOD__ . ' : ' . self::ERROR_UNABLE . PHP_EOL;
$message .= strip_tags($filename) . PHP_EOL;
throw new Exception($message);
}
$this->file = new SplFileObject($filename, $mode);
}
/**
* @return \Generator|int
*
* References SplFileObject method to read the file one line
* at a time with fgets.
*
* Suitable for smaller text files like Csvs and / or
* include line feeds.
*/
protected function fileIteratorByLine() {
$count = 0;
while (!$this->file->eof()) {
yield $this->file->fgets();
$count++;
}
return $count;
}
/**
* @param $numBytes
*
* @return \Generator|int
*
* References SplFileObject method to read the file one line
* at a time with freads.
*
* Suitable for larger binary files.
*/
protected function fileIteratorByLength($numBytes) {
$count = 0;
while (!$this->file->eof()) {
yield $this->file->fread($numBytes);
$count++;
}
return $count;
}
protected function fileIteratorCsv() {
$count = 0;
while (!$this->file->eof()) {
yield $this->file->fgetcsv();
$count++;
}
return $count;
}
/**
* @param string $type
* @param null $numBytes
*
* @return NoRewindIterator
*/
public function getIterator($type = 'ByLine', $numBytes = null) {
if (!in_array($type, $this->allowed_types)) {
$message = __METHOD__ . ' : ' . self::ERROR_TYPE . PHP_EOL;
throw new InvalidArgumentException($message);
}
$iterator = 'fileIterator' . $type;
return new NoRewindIterator($this->$iterator($numBytes));
}
}
$largeFile = new LargeFile($file);
// tell it use the CSV iterator
$iterator = $largeFile->getIterator('Csv');
// start iterator and pull out header row as $rawHeaders
$rawHeaders = $iterator->current();
$headerIterator = new \ArrayIterator;
foreach ($rawHeaders as $header) {
$headerIterator->append(strtolower("`$header`"));
}
$headers = $headerIterator->getArrayCopy();
// move pointer to the data rows
$iterator->next();
// loop through each row
foreach( $iterator as $row ) {
// do stuff with each row
print_r($row);
}