为什么这个PHP会导致执行超时?

3

我刚刚发布了一个我写的WordPress插件的第一个版本,有人报告说使用我的插件的至少一个人收到了一个执行超时错误,引用了这个代码块:

function getNumericAttributeFromHTML($htmlElement, $attribute){
    $attrStartPos = stripos($htmlElement, $attribute) + strlen($attribute);

    $strOffset = 0;
    $searchWithin = substr($htmlElement, $attrStartPos);

    while(!(is_numeric($searchWithin[$strOffset]))){
        $strOffset++;
    }
    $attrStartPos += $strOffset;

    $strOffset = 0;
    $searchWithin = substr($htmlElement, $attrStartPos);

    while((is_numeric($searchWithin[$strOffset]))){
        $strOffset++;
    }

    return substr($htmlElement, $attrStartPos, $strOffset);
}

这个函数在页面上每张图片会被调用两次。我是不是太低效了,还是他们的主机真的很糟糕?

感谢您提供的任何帮助。


你能展示一下 $htmlElement$attribute 在超时时的例子吗? - Grzegorz
你这样做的原因是什么,而不是使用一点DOM直接提取属性,然后将整个检索到的“文本”传递给is_numeric? - Marc B
也许使用正则表达式会更好地解决这个问题。这个函数到底应该做什么?获取一个名为$attribute的属性的值吗? - The Maniac
@MarcB 我有点 PHP 新手,所以我不太确定该怎么做。除此之外,插件非常小,我不想在其中添加太多复杂性。 - Greg Brown
3个回答

2

while(!(is_numeric($searchWithin[$strOffset]))) 如果$searchWithin中没有数字字符,将会无限循环

注意问题可能出现在其他地方。

为了准确定位实际问题,我建议您从错误中获取可复现的步骤,并使用分析工具来分析代码。您一定会找到问题所在。


非常完美的答案,但我先看到了标记的回复。不过还是非常感谢你的帮助。 - Greg Brown

1

你有一个无限的while循环。你只是增加了$strOffset的值,而没有改变$searchWithin[$strOffset]的值,所以如果它不是数字,它永远不会成为数字,并且会一直陷入循环。


is_numeric() 在未定义的值上是 false,因此一旦到达字符串末尾,它会自动终止。 - Marc B
我想假设一个人有有效的HTML可能太过分了,但是假设这样,即使在字符串的末尾,该值也必须在某个时候变为非数字,对吗? - Greg Brown
3
但条件是只要不是数字就继续循环。所以如果返回值为false,那么就会执行"while not false",也就是"while(true) {$strOffset++}",这样就造成了无限循环。 - AlienWebguy
1
啊,是啊。我真傻。提醒我晚点用Windex擦我的眼镜。 - Marc B
啊...好主意,@AlienWebguy。我会找到另一种方法来完成那个部分的! - Greg Brown

0

如果它导致超时,那么你有一个额外大或无限循环。你在这里有2个循环,请检查它们是否无限。

如果这不是问题,通过在脚本开头添加以下内容来增加最大执行时间:

ini_set('max_execution_time', 36000); //3600 seconds = 1 hour

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接