【问题标题】:Memory leak in phpphp内存泄漏
【发布时间】:2012-07-13 18:17:47
【问题描述】:

我无法理解我的这部分代码导致内存泄漏的原因:

for($i=0; $i<count($values); $i++){
        $values[$i] = addslashes($values[$i]);
}

为了将代码放在上下文中,我有一个先前构建的名为 values 的数组,其中包含要插入数据库的所有值。所有字段都是字符串,所以我需要转义所有字段,对于这个应用程序,addlashes 或 mysql_real_escape_string 是一个不错的选择 imo。

现在奇怪的是,只要我添加了上面显示的部分,我就会收到这样的消息:

PHP Fatal error:  Allowed memory size of 134217728 bytes exhausted (tried to allocate 24 bytes)

我知道这会产生内存泄漏,但我不知道为什么。

深入研究,我注释掉了 for 循环中的唯一一行,出于好奇而留下了 for 语句,泄漏就消失了。任何想法这可能意味着什么?

PS:字符串都是UTF8编码的,会不会有问题?

编辑:

数组包含类似这样的内容:

Array ( 
    [dossier] => 002A 
    [permis] => 
    [adresse] => 18, rue Bellevue
    [ville] => Ste-Anne-des-Lacs (Québec)
    [province] =>
    [code_postal] => J0R 1B0
    [numero_centrale] => N/A
    [routes] => De la Gare, droite chemin Avila jusqu'au bout et droite chemin Ste-Anne-des-lacs sur 1,8 km et droite sur Bellevue.
) 

【问题讨论】:

  • 阵列有多大?以及数组的每一项?
  • 你用addslashes做什么?我感觉你做错了。
  • 虽然它不能解决你的内存问题,但你不应该把count 放在这样的循环中;始终在循环之前将计数分配给某个变量,并在循环中使用该变量。按照您编写的方式,count() 将通过$values 为每次迭代调用
  • @Wug, mysql_real_escape_string 导致同样的问题,我先使用它,但我切换到添加斜杠来检查它是否有效
  • @AdamSack 我不知道我在想什么哈哈

标签: php memory-leaks addslashes


【解决方案1】:

您的数组有字符串键,但您正在检查/分配数字键。正如@nickb 所指出的,每次添加数字键时,count($values) 都会增加一,因此您有一个无限循环。因此内存耗尽。

使用调试器检查,或者更好的是,切换到foreach 循环或array_* 函数之一(array_walk()array_map() 等,具体取决于您要执行的操作)。

@Jeremy 正确地指出您不应该使用 addslashes() 来转义您的字符串。看看mysqli_real_escape_string()(正如他建议的那样),或者更好的是,如果可以的话,考虑使用PDO

【讨论】:

  • @Jeremy 这是真的(有点——如果可以的话,你应该真的使用 PDO 并且根本不插入字符串),但不是发帖人要问的。
  • 对正在发生的事情的更准确解释是:因为每次迭代都会调用count() 并且总是添加新元素(count() 开始于8,每次迭代加1,而$i从0开始),循环是无限循环。
  • 是的,我同意 Trott,我更喜欢 PDO,它已经完成了所有这些,但在这种情况下,我被其他人的决定所困扰
  • 在答案中添加了@Jeremy 的 cmets 和我自己的。 (希望他会考虑撤消反对票,但无论如何,无论如何。:-))
  • 添加了@nickb 比我最初对无限循环源的解释更好的解释。
【解决方案2】:

尝试改用array_walk

另外,不要指望每个循环。在将其放入有条件的循环之前获取计数。由于这是针对数据库的,因此您应该真正使用:mysqli_real_escape_string

【讨论】:

  • 使用 mysqli_real_escape_string 无助于问题中提到的内存问题。
  • 这是转义数据的正确方法。问题是它首先做错了
  • 如果你想顺便提一下也没关系。但是你的回答并没有回答这个问题。问题是字符串键,而不是整数键。提及 array_walk 和 real_escape_string 并不能回答问题。
  • 同意,但逻辑一开始就是错误的。指导某人做错误的解决方案并不能使其正确。教他们正确的方法更有意义
  • 那么你提供的数据不是答案,而是评论。是的?我邀请您单击页面顶部的“元”链接。在那里,我们可以讨论语义以及如何提供数据来帮助人们成长,同时仍然回答他们想要的问题。
猜你喜欢
  • 2016-02-10
  • 2023-03-17
  • 2012-04-17
  • 2012-01-12
  • 2017-01-28
  • 2016-03-30
  • 1970-01-01
  • 2013-09-02
  • 2014-09-22
相关资源
最近更新 更多