Самый быстрый способ прочитать файл csv

Я ищу очень быстрый способ чтения CSV-файла. Моя структура данных выглядит так:

timestamp ,float     , string    ,ip          ,string
1318190061,1640851625, lore ipsum,84.169.42.48,appname

и я использую fgetcsv для чтения этих данных в массивы.

Проблема: Производительность. На регулярной основе скрипт должен прочитать (и обработать) более 10 000 записей.

Моя первая попытка очень проста:

//Performance: 0,141 seconds / 13.5 MB

while(!feof($statisticsfile)) 
    {
    $temp = fgetcsv($statisticsfile);
    $timestamp[] = $temp[0];
    $value[] = $temp[1];
    $text[] = $temp[2];
    $ip[] = $temp[3];
    $app[] = $temp[4];
    }

Моя вторая попытка:

//Performance: 0,125 seconds / 10.8 MB

while (($userinfo = fgetcsv($statisticsfile)) !== FALSE) {
   list ($timestamp[], $value[], $text, $ip, $app) = $userinfo;
}
  1. Есть ли способ еще больше повысить производительность, или мой метод настолько быстр, насколько это возможно?
  2. Вероятно, более важно: есть ли способ определить, какие столбцы читаются, например. иногда нужны только метки времени, столбцы с плавающей запятой. Есть ли лучший способ, чем мой способ (посмотрите на мою вторую попытку :)

Спасибо :)


person Nyoman    schedule 09.10.2011    source источник
comment
10 000 строк CSV — это НИЧЕГО. Модификации, которые вы делаете, сократят (максимум) несколько миллисекунд процесса, который в любом случае занимает всего децисекунды. Задайте этот вопрос о микрооптимизации, когда вы достигнете миллионов или миллиардов строк.   -  person Marc B    schedule 10.10.2011
comment
Пожалуйста, просмотрите множество существующих вопросов по SO, показывающих, как читать файлы CSV с помощью PHP. Возьмите примеры, приведенные в ответах, и сравните/профилируйте их в реальных условиях. Затем используйте то, что является самым быстрым для вашего сценария.   -  person Gordon    schedule 10.10.2011
comment
@Gordon Не могли бы вы указать более быстрый / лучший пример из этих вопросов. Я прочитал их за последние пару дней, и вот результат.   -  person Nyoman    schedule 10.10.2011
comment
@Nyoman, даже если бы я хотел сделать вашу работу за вас, я бы не смог, потому что я не могу профилировать различные возможные решения (fgetcsv, implode, SplFileObject, sscanf) в вашей реальной среде. Вы должны сделать это самостоятельно.   -  person Gordon    schedule 10.10.2011
comment
$data = array_map("str_getcsv", file($filename)); — самый быстрый метод, так как он считывает сразу весь CSV-файл.   -  person mario    schedule 10.10.2011
comment
если вам не нужно помещать в память весь проанализированный файл (как вы делаете в своем примере, добавляя каждую строку в массивы $col[]=$field), использование одной строки сразу улучшит производительность...   -  person    schedule 10.10.2011
comment
@mario К сожалению, str_getcsv недоступен...   -  person Nyoman    schedule 10.10.2011
comment
@Nyoman: в руководстве есть несколько эмуляций, PHP_Compat или upgradephp. Хотя вы не получите преимущества в производительности без встроенной версии.   -  person mario    schedule 10.10.2011
comment
@wes Не могли бы вы дать мне подсказку? Я не молчу, получая ваш подход ..   -  person Nyoman    schedule 10.10.2011
comment
@Nyoman в вашем примере вы храните все часовые пояса в одном массиве ( list ($timestamp[] ... ). Массив $timestamp[] (и другие) будет огромной причиной замедления. но, может быть, вы не нужно запоминать весь список меток времени в одном массиве, чтобы делать то, что вы пытаетесь сделать   -  person    schedule 10.10.2011
comment
@Nyoman, связанный с моим предыдущим примером, я могу предложить альтернативу сложным результатам по сравнению с реализацией php ... вы можете использовать драйверы PDO для чтения и выполнения сложных запросов к базам данных csv, или вы можете читать базу данных csv, как вы это делаете (с fgetcsv) и поместите его в одну базу данных sqlite3 в памяти (it.php.net /manual/ru/sqlite3.construct.php)   -  person    schedule 10.10.2011


Ответы (2)


Какова длина самой длинной очереди? Передайте это как второй параметр в fgetcsv(), и вы увидите самое большое улучшение.

person Robin Millette    schedule 13.09.2012

Проверьте время, когда PHP прочитал этот файл:

Если файл большой, переместите его на виртуальный диск или SSD.

  1. [..]иногда только метка времени

Что-то вроде этого

preg_match_all('#\d{10},\d{10}, (.*?),\d.\d.\d.\d,appname#',$f,$res);

print_r($res);
person user956584    schedule 10.10.2011