有很多if语句会降低php的渲染速度吗?

am46iovg  于 2023-06-20  发布在  PHP
关注(0)|答案(7)|浏览(172)

我想知道我的PHP代码中复杂的if/else结构是否是一个糟糕的设计决策。有很多if语句会使PHP运行缓慢,网站加载缓慢等吗?
这就是代码:(我不知道WordPress如何处理is_page等)

<?php

if (is_page()) {
//
    if (is_page(122)) {
    //subscribe page
    echo "subscribe page";

    }

    elseif (is_page(1263)) {
    //photography course
    echo "photography course page";

    }

    elseif (is_page(array(210,184,128))) {
    //210 copyright policy, 184 privacy policy, 128 contact
    echo "this is either copyright policy, privacy or contact page!";
    //nothing happens here, we don't need social buttons on these pages.
    }

    elseif (is_page(array(379,71,7,45,124,8,105,175,9,125,110))) {
    //379 photo galleries, 71 car photos, 7 conceptual, 45 event photos, 124 fashion, 8 landscape, 105 misc, 175 journalism, 9 portrait, 125 street photography, 110 travel
    echo "gallery pages and albums";

    }

    else {
    //any other page
    echo "any other page";

    }
//
}

elseif (is_single()) {
//
    if (in_category(array(147,196,35))) {
    //147 car photography, 196 car wallpapers, 35 photo stories
    echo "photo posts";

    }
    else {
    //any other post
    echo "any other post";

    }
//
}

elseif (is_archive()) {
//
    //any category
    echo "this is archive template"

}
//
?>
dnph8jn4

dnph8jn41#

事实上,在大多数情况下,它实际上会加快速度(因为它允许跳过代码块)。
大量的if语句唯一会减慢速度的情况是,您正在检查的条件需要处理。例如:

while (true)
{
    if (count($some_array) == 0) { break; }
    /* some other code */
}

每次循环迭代都会检查count($some_array) == 0。这意味着每次传递,PHP都必须手动count$some_array中的项目数,因为它可能已经更改。这也适用于for循环中的停止条件。这是因为for循环总是可以重写为while循环:

for ([INITIALIZER_ACTION]; [CONDITION]; [POST_ITERATION_ACTION]) { [CODE]; }

就像...

[INITIALIZER_ACTION];
while ([CONDITION]) { [CODE]; [POST_ITERATION_ACTION]; }

如果你正在考虑将一堆if语句合并成一个:别,你不会得到任何好处的。PHP会短路,这意味着如果它到达一个点,它知道结果会是什么,它会跳过其余的。
例如,考虑$a = 5; if ($a > 0 || $b > 100 || $c > 200) {}
一旦PHP看到$a > 0条件得到满足,整个语句就会被解析为true(因为使用了OR值),并且不会检查$b > 100$c > 200
回答你的问题:除非你有大量的条件,每个条件都需要复杂的计算或有副作用,否则你通常可以认为它们的数量是无关紧要的。
但是,正如其他人所指出的,如果语句太多,会降低代码的可读性。在许多情况下,如果您可以删除条件而不影响代码的行为,那么您一开始就不需要它。

bz4sfanl

bz4sfanl2#

我刚刚从WPShout中看到了一个非常有趣的article,它使用了一个非常人性化的类比来邀请我们更聪明地编写代码,以及为什么深度嵌套的if { .. }语句不仅会降低性能,还会降低代码的可维护性。如果逻辑是性能感知的,没有不必要的臃肿的迭代检查,那么很可能您最终会得到一个组织得很好的、响应性更好的代码。
代码示例(摘自文章)
“让我们通过看两个简单的代码示例来具体说明这一点:首先是泡沫式,然后是网关式”。

    • 不好:泡泡风格**
$is_first_thing_working = true;
$is_second_thing_working = true;
$is_third_thing_working = true;
$is_fourth_thing_working = true;

if( $is_first_thing_working === true ) {
    if( $is_second_thing_working === true ) {
        if( $is_third_thing_working === true ) {
            if( $is_fourth_thing_working === true ) {
                return 'Working properly!';
            }
            else {
                return 'Fourth thing broken.';
            }
        }
        else {
            return 'Third thing broken.';
        }
    }
    else {
        return 'Second thing broken.';
    }
}
else {
    return 'First thing broken.';
}
    • 好:网关风格**
$is_first_thing_working = true;
$is_second_thing_working = true;
$is_third_thing_working = true;
$is_fourth_thing_working = true;

if( $is_first_thing_working !== true ) {
    return 'First thing broken.';
}

if( $is_second_thing_working !== true ) {
    return 'Second thing broken.';
}

if( $is_third_thing_working !== true ) {
    return 'Third thing broken.';
}

if( $is_fourth_thing_working !== true ) {
    return 'Fourth thing broken.';
}

return 'Working properly!';
    • 示例注解**

上面两个代码片段之间的区别归结为一个关键的区别:
bubble方法会询问重要的条件是否为真,并且仅在它们为真时才运行代码。
网关方法询问重要条件是否为假,如果为假,则立即为每个条件发出退出指令。
bubble方法强制嵌套,因为在得到要运行的代码之前,必须检查**"true,true,true,true"。每个"true"**检查都是一个嵌套级别--您的代码必须存在于其中的一个条件。

    • gateway方法没有嵌套:如您所见,代码的逻辑深度永远不会超过一层。这是因为一旦通过了给定的网关,我们就可以完全忘记它。换句话说,由于我们在$is_first_thing_working检查后没有退出,我们自动知道$is_first_thing_working对于其余代码是true**。

“这就像现实生活:如果你在历史课上坐在我旁边,我知道你是一个人类,是我高中的学生,等等--否则你一开始就不会在我的班上。不用查了。”

vjhs03f7

vjhs03f73#

if子句是性能方面最便宜的操作之一。
但是,你在if子句中放入的东西可能会非常慢。
例如,if (true) { ... }将非常快,但单个if (calculatePi()) { ... }将永远持续下去。if本身是如此之快,你永远不必担心它,此外,几乎所有你做的事情都涉及到许多if,例如当你做forwhile循环或switch语句。所有这些本质上都包含if(一个或多个)。
至于设计,许多if可能会让其他开发人员感到困惑,这取决于您编写的内容和编写方式。有时候你最好使用switch/case语句或其他一些应用程序工作流,但说实话,一堆if可能比你想到的任何类型的结构执行得更快。但只有当你唯一关心的是表现时,才能把这一点放在心上。我重复一遍,设计软件主要不是关于性能。好的软件设计是关于其他方面的,比如可维护性,即。阅读并成功升级代码是多么容易。
简而言之,如果您正在优化性能,就不要费心去减少if的数量。而是专注于if s在询问什么,或者根据它们返回true还是false会发生什么。
希望能帮上忙。

jvidinwx

jvidinwx4#

在大多数情况下,非常复杂的if/else结构表示设计不好。你可以更好地专注于改进一个糟糕的设计,而不是优化,premature optimization is the root of all evil!
如果你给予一个你正在谈论的代码类型的例子,也许可以给出一个更详细的答案。

ej83mcc0

ej83mcc05#

问题不在于有太多的if else语句,而在于1)它们的顺序和2)你的条件有多有效
1)If else状态应按条件概率的降序排列。在我的wp_posts数据库表中,80%的记录都有post_status的“draft”、“pending”、“trash”等。而不是“发布”。大约40%的记录“发布”为post_type。所以,没有理由

if ($post_type=="post"&&$post_status=="publish") {
    doA();
} elseif ($post_type!="post"&&post_status=="publish") {
    doB():
} elseif ($post_type=="post"&&post_status!="publish") {
    doC();
} else {
    doD();
}

但应该是相反的顺序
关于2),WordPress的数据库模式表明in_category()会很慢。如果是您自己编写的查询,当然,这取决于您的查询的效率

slwdgvem

slwdgvem6#

在某种程度上……是的。
我这样说是考虑最坏的情况,在这种情况下,一个非常大的模型对象有很多条件。在这里,代码必须经过所有的条件检查,这最终会减慢代码的速度。
条件语句给并行化和向量化带来困难,并且一长串IF-THEN也会导致指令缓存未命中和其他影响。但如果这是使代码最清晰的原因,那么就使用它。

bvn4nwqk

bvn4nwqk7#

对于python:

def check(string):
  if string == "hi":
    return string
  elif string == "hey":
    return string
  elif string == "hello":
    return string

# on colab  
%timeit check("hi")
%timeit check("hey")
%timeit check("hello")

#output.                   time can vary
>>>130 ns ± 37 ns per loop (mean ± std. dev. of 7 runs, 10000000 loops each)
>>>146 ns ± 50.1 ns per loop (mean ± std. dev. of 7 runs, 10000000 loops each)
>>>153 ns ± 39.7 ns per loop (mean ± std. dev. of 7 runs, 10000000 loops each)

相关问题