【问题标题】:PHP Memory exceeded while writing to array in a loop循环写入数组时超出 PHP 内存
【发布时间】:2016-04-22 16:13:18
【问题描述】:

我需要更新循环内数组中的值。通常这可以正常工作,但是有关此循环的某些内容会导致内存最大化。

while ($watering_window['total_run_time'] > $water_window_total)
{
    foreach ($master_schedule as &$_ms)
    {
      $current_soak_time = $_ms['between_starts'] - $_ms['total_run_time'];
      if ($current_soak_time > 0)
      {
          $new_soak_time = ceil($current_soak_time * 0.9);
          $_ms['between_starts'] = $_ms['total_run_time'] + $new_soak_time;
          $watering_window['total_run_time'] -= $current_soak_time - $new_soak_time;
      }
    }
}

关于写入$_ms['between_starts'](现有密钥)的某些内容导致了内存问题。如果我将其更改为写入一个新键(如$_ms['between_starts_new'],没有内存问题。我还尝试向它写入一个常量值(而不是数学),但它仍然超时。

【问题讨论】:

  • if ($current_soak_time > 0) 的大括号似乎没有闭合
  • 谢谢你,jcorry。那是一个转录错误。在我的实际代码中,如果当前浸泡时间不 > 0,则有一个条件会向用户显示一条消息。
  • 是无限循环吗? $watering_window['total_run_time'] > $water_window_total 是否曾经评估为假?使用调试器可以更轻松地解决此类问题...
  • 您是否尝试过删除对您的 &$_ms 值的引用?这可能是导致$_ms['between_starts'] 膨胀的原因(连续递增),进而导致$current_soak_time 膨胀,因此不允许$watering_window['total_run_time'] > $water_window_total 返回false。还是因为其他原因需要引用$_ms
  • $watering_window['total_run_time'] 应该越来越小,但它不能因为$_ms['between_starts'] 越来越大。反过来,正因为如此,$current_soak_time 也是如此。反正我是这么看的。在这种情况下,您必须重写逻辑并确定引用是否真的必要,因为它直接影响循环的结果。

标签: php arrays loops


【解决方案1】:

您需要增加memory_limit。 在 php 脚本的顶部添加以下内容:

<?php
ini_set('memory_limit','256M');
...

根据您的需要调整值。

【讨论】:

  • 我的内存限制当前设置为 134,217,728 字节。一定有办法在不改变内存限制的情况下解决问题。
  • 是的,您可能需要更改您的代码,但我不知道您要做什么...
  • 是的,这段代码中有大量的领域知识。我希望无论我做错了什么都足够明显,以至于理解代码的作用并不重要……本质上,我在迭代地减少时间,直到满足 while 循环的条件。每次减少它时,我都需要更新数组,以防它最后一次更新。也许有更好的方法来完成最后一部分?
【解决方案2】:

在设置之前尝试取消设置导致问题的键。

foreach ($master_schedule as &$_ms)
{
  $current_soak_time = $_ms['between_starts'] - $_ms['total_run_time'];
  if ($current_soak_time > 0)
  {
      $new_soak_time = ceil($current_soak_time * 0.9);
      unset($master_schedule['between_starts']);
      $_ms['between_starts'] = $_ms['total_run_time'] + $new_soak_time;
      $watering_window['total_run_time'] -= $current_soak_time - $new_soak_time;
  }

}

【讨论】:

  • 很好的建议。但它似乎并没有解决内存问题。我也用你最新的编辑试过了。
  • @JessycaFrederick,你有没有试过在$_ms 循环查看它是否在增长时转储它的值?您是否也尝试过在不使用参考的情况下这样做?
  • 我认为我没有尝试过任何一种方法,因为我不确定你的意思。 (我不是经验丰富的程序员。)
  • 我尝试在没有后续 write 语句的情况下自行取消设置值(如您所示),它会创建一个无限循环。
  • 哦,好的。因此,不要在代码中发生错误之前使用echo 之类的东西,而是使用var_dump($_ms)。它应该打印array 的内容,以便您可以看到代码执行期间发生的情况。如果您不知道我在说什么,请暂时不要担心。只需查明$_ms 数组是否正在增长,或者是否有任何其他数组正在增长。因为这是最有可能导致问题的原因。
猜你喜欢
  • 2015-11-18
  • 1970-01-01
  • 2011-01-26
  • 2013-06-16
  • 1970-01-01
  • 2010-10-07
  • 1970-01-01
  • 1970-01-01
  • 2022-11-13
相关资源
最近更新 更多