Любителям MS-Excel посвещается

WMix

герр M:)ller
Партнер клуба
PHP:
   function toArray( \SplFileObject $input ){
        $content = '';
        while( !$input->eof() ){
            $content .= $input->fread();
        }
        $converted = substr(
            iconv('UTF-16LE', 'UTF-8', $content),
            3
        );
        $memory = new \SplFileObject('php://memory');
        $tmp = $memory->openFile('rw');
        $tmp->fwrite( $converted );
        $tmp->fseek(0);
        $data = function() use ($tmp){
            while (!$tmp->eof()) {
                yield $tmp->fgetcsv("\t");
            }
        };
        return $data();
    }

   function fromArray( $input, \SplFileObject $datei ){
        $memory = new \SplFileObject('php://memory');
        $tmp = $memory->openFile('rw');
        $tmp->fwrite(chr(0xEF).chr(0xBB).chr(0xBF));
        foreach ($input as $row){
            $tmp->fputcsv($row, "\t");
        }
        $tmp->fseek(0);
    
        $content = '';
        while(!$tmp->eof()){
            $content .= $tmp->fread();
        }
        $datei->openFile('w');
        $datei->fwrite( iconv('UTF-8', 'UTF-16LE', $content) );
        return $tmp;
    }
    fromArray($array, new \SplFileObject('php://output'));
    toArray( new \SplFileObject('php://input') );
 
Последнее редактирование:

AnrDaemon

Продвинутый новичок
Я не очень понял, зачем это делать?

P.S.
И я бы использовал \SplFileInfo а не \SplFileObject…
 

AnrDaemon

Продвинутый новичок
У меня его вообще нет. Но глядя на твой код, я не понимаю, зачем ты это делаешь.
Файлы Excel это либо compound object, либо ZIP из кучи файлов.
В обоих случаях смысла переводить бинарные данные из UTF-16 в UTF-8 - получим мусор.
 

WMix

герр M:)ller
Партнер клуба
@AnrDaemon, обьясни это Microsoft разговор про CSV кстати
 
Последнее редактирование:

WMix

герр M:)ller
Партнер клуба
Генератор для красоты воткнул и забыл потом убрать? ;)
для обычны csv было так
PHP:
    public function toArray( \SplFileObject $input ){
        $data = function() use ($input){
            while (!$input->eof()) {
                yield $input->fgetcsv();
            }
        };
        return $data();
    }
   
    public function fromArray( $input, \SplFileObject $datei ){
        $datei->openFile('w');
        foreach ($input as $row){
            $datei->fputcsv($row);
        }
        return $datei;
    }
и да там был генератор. ну да пусть и будет
а что с UTF-16LE делать?
 

WMix

герр M:)ller
Партнер клуба
@AnrDaemon, тут понятно
PHP:
file_put_contents('test.csv', 'hello,привет');

$fp = fopen('test.csv', 'r');
stream_filter_append($fp, 'convert.iconv.UTF-16LE/UTF-8', STREAM_FILTER_ALL);
fpassthru($fp);
fclose($fp);
а тут не догоняю
PHP:
class Csv{

    public function toArray( \SplFileObject $input ){
        $data = function() use ($input){
            while (!$input->eof()) {
                yield $input->fgetcsv();
            }
        };
        return $data();
    }

    public function fromArray( $input, \SplFileObject $file ){
        $file->openFile('w');
        foreach ($input as $row){
            $file->fputcsv($row);
        }
        return $file;
    }
}

$csv = new Csv();
$array = [['hello', 'привет']];

$file = (new \SplFileInfo('php://memory'))->openFile('rw');
$file = $csv->fromArray($array, $file);

$file->fseek(0);
$content = "";
while (!$file->eof()) {
    $content .= $file->fread(1024);
}
echo $content; // hello,привет

$file->fseek(0);
$newArray = $csv->toArray( $file );

foreach($newArray as $row){
    print_r($row); // ['hello', 'привет']
}
 

AnrDaemon

Продвинутый новичок
Надо создать стрим враппер и открывать через него.
Как именно, не помню. Давно ставил эксперименты, и документация с тех пор лучше не стала :(
Но принцип был в том, что можно сохранить себе кучу нервов, скрыв все трансляции под капотом.
 
Сверху