在while循环中添加数组时PHP会冻结

时间:2012-08-19 16:23:56

标签: php arrays while-loop

我有一个260k行csv文件,有两列。我已经使用fgetcsv读取了csv文件,并且有一个while循环,它读取文件中的每一行。在循环中,我试图将第二列中的值添加到数组中。

当我将行添加到数组中时,我的PHP冻结并且没有完成。我已经完成了调试,并且值被添加到数组中,所以我知道添加到数组和while循环工作,但我不知道为什么它会冻结。

如果我删除了行,则while循环完成通过260k行,然后处理文件的其余部分。

这是我的代码:

$amountRecords = 0;
$totalValue = 0;
$valueArray = array();

// reads in csv file
$handle = fopen('Task1-DataForMeanMedianMode.csv', 'r');
// to skip the header names/values
fgetcsv($handle);

// creates array containing variables from csv file
while(($row = fgetcsv($handle, "\r")) != FALSE)
{

    /*
    echo "ROW CONTAINS: ";
    var_dump($row[1]);
    echo "<br />";
    */

    $valueArray[] = $row[1];

    /*
    echo "VALUEARRAY NOW CONTAINS: ";
    var_dump($valueArray);
    echo "<br />";
    */

    $totalValue = $totalValue + $row[1];
    $amountRecords++;

}

csv文件样本:

ID,Value
1,243.00
2,243.00
3,243.00
4,243.00
5,123.11
6,243.00
7,180.00
8,55.00
9,243.00
10,55.00

4 个答案:

答案 0 :(得分:1)

出现内存不足错误,有两种常规方法。像往常一样,这些选择,你可以选择容易但错误和艰难但正确的选择。简单但错误的解决方案是将your memory limit提高到适当的水平:

ini_set('memory_limit', '64M');

更好(尽管更难)的解决方案是重新设计算法,而不需要那么多的内存。这显然是更可持续和更强大的方法。要正确执行此操作,您需要评估您正在构建的阵列需要执行的操作。例如,我编写了类似的脚本,将行导入数据库。而不是构建一个巨大的数组和然后插入,我分批完成它,在那里我构建了一个50-100行的数组,然后插入并清除了数组(释放内存以便重复使用)

伪代码:

for(each row in file) {
  $rows_cache[] = $row[1];
  if(count($rows_cache) >= 50) {
    insert_these($rows_cache);
    $rows_cache = array();
  }
}

答案 1 :(得分:0)

你的第一行是字符串,也许可以尝试添加

while(($row = fgetcsv($handle, "\r")) != FALSE)
{

    if(is_numeric($row[1]))
    { 
        $valueArray[] = $row[1];

        $totalValue = $totalValue + $row[1];
        $amountRecords++;
    }
}

答案 2 :(得分:0)

为什么不放弃这条线:

$totalValue = $totalValue + $row[1];

从你的循环内部,而不是使用:

$totalValue = array_sum($valueArray);
完成循环后

答案 3 :(得分:0)

不是问题,但是

while(($row = fgetcsv($handle, "\r")) != FALSE)

可以改写为

while($row = fgetcsv(...)) 

代替。不需要显式的错误检查 - 如果fgetcsv返回false,则while循环将终止。此外,这个版本更清晰,并没有风险。如果你忘记了fget部分周围的(),那么你将完成相当于$row = (fgetcsv() != false)并且只是得到一个布尔值。