3

当我将以下代码附加到我的脚本时,我的页面加载时间从 650-700 毫秒变为 1.5-1.6 秒:

$authpts = array();
foreach ($obj["pro"] as $key => $val) {
    $c_recs = count($recs);
    for ($i=0; $i<$c_recs; $i++) {
        if ($recs[$i][0] === $key) {
            $wr = $recs[$i][1];
            break;
        }
    }
    $c_val = count($val);
    for ($i=0; $i<$c_val; $i++) {
        if (!array_key_exists($val[$i]["authid"], $authpts))
            $authpts[$val[$i]["authid"]] = 0;
        $ratio = 0;
        if (strlen($c_wr) > 0) {
            $ratio = comparetime($val[$i]["time"], $wr);
            $ratio = $ratio[0];
        }
        $rbonus = ($ratio > 0) ? pow($ratio, (2 / $ratio)) : 0;
        $authpts[$val[$i]["authid"]] = $authpts[$val[$i]["authid"]] + ($c_val - $i) * (1 + $rbonus);
    }
}

现在,如果我的脚本在这里结束,这可能是可以接受的,但在此之后还需要发生三个类似的循环。目前,如果我启用所有功能,页面加载大约需要 15 秒,这是完全不可接受的。

$obj["pro"]有大约 1500 个条目要迭代,$recs大约有 3000 个。我已经尽力优化它,但想知道是否有更有效的方法来执行相同的功能。

基本上我需要在数组中找到任何出现的字符串(来自外部数组的键$obj["pro"]$recs(如果存在)(如果有的话,应该只有一个匹配项;这就是我在找到匹配项时中断的原因),然后获得一个的匹配索引中包含的对应值$recs

下一步是在$authpts初始值为 0(点)的不同初始空数组 ( ) 中创建一个新数组键,然后,如果找到匹配项,则查看每个外部数组的键值并比较其中一个( time) 使用存储的值$recs来计算表示绩效的比率奖金。

$authpts最后一步是从指数和比率奖金(如果适用)中添加一些点数。

请注意,当此代码在 javascript 中时,完成所需的时间要少得多。

==========================

编辑:这是整个 calcpoints 函数(我不会描述它,因为信息太多,大部分是不言自明的):

function calcpoints($obj, $recs) {
    global $points, $wpnspeeds;
    $authpts = array();
    foreach ($obj["pro"] as $key => $val) {
        $c_recs = count($recs);
        for ($i=0; $i<$c_recs; $i++) {
            if ($recs[$i][0] === $key) {
                $wr = $recs[$i][1];
                break;
            }
        }
        $c_val = count($val);
        for ($i=0; $i<$c_val; $i++) {
            if (!array_key_exists($val[$i]["authid"], $authpts))
                $authpts[$val[$i]["authid"]] = 0;
            $ratio = 0;
            if (strlen($wr) > 0) {
                $ratio = comparetime($val[$i]["time"], $wr);
                $ratio = $ratio[0];
            }
            $rbonus = ($ratio > 0) ? pow($ratio, (2 / $ratio)) : 0;
            $authpts[$val[$i]["authid"]] = $authpts[$val[$i]["authid"]] + ($c_val - $i) * (1 + $rbonus);
        }
    }
    foreach ($obj["nub"] as $val) {
        $c_val = count($val);
        for ($i=0; $i<$c_val; $i++) {
            if (!array_key_exists($val[$i]["authid"], $authpts))
                $authpts[$val[$i]["authid"]] = 0;
            $authpts[$val[$i]["authid"]] = (array_key_exists("gc", $val[$i])) ? $authpts[$val[$i]["authid"]] + ($c_val - $i) * pow(0.98, $val[$i]["gc"]) : $authpts[$val[$i]["authid"]] + ($c_val - $i);
        }
    }
    foreach ($obj["wpn"] as $val) {
        $c_val = count($val);
        for($i=0; $i<$c_val; $i++) {
            if (!array_key_exists($val[$i]["authid"], $authpts))
                $authpts[$val[$i]["authid"]] = 0;
            $wsw = 1;
            if (array_key_exists("weapon", $val[$i]) && array_key_exists($val[$i]["weapon"], $wpnspeeds))
                $wsw = (250 - $wpnspeeds[$val[$i]["weapon"]]) / (250 - $wpnspeeds["awp"]);
            $authpts[$val[$i]["authid"]] = (array_key_exists("gc", $val[$i])) ? $authpts[$val[$i]["authid"]] + ($c_val - $i) * (pow(0.98, $val[$i]["gc"]) + $wsw) : $authpts[$val[$i]["authid"]] + ($c_val - $i) * (1 + $wsw);
        }
    }
    foreach ($authpts as $key => $val) {
        $val = round($val, 2);
        foreach ($obj["pro"] as $k2 => $v2) {
            $c_v2 = count($v2);
            for ($i=0; $i<$c_v2; $i++) { 
                if (trim(strtolower($v2[$i]["authid"])) == trim(strtolower($key)))
                    $res = $v2[$i];
            }
        }
        if(isset($res))
            $points[$res["name"]] = $val;
    }
    uasort($points, function($a, $b) {
        if ($a == $b)
            return 0;
        return ($a > $b) ? -1 : 1;
    });
    return $points;
}
4

1 回答 1

3

创建一个关联数组,其中包含$recs循环之前的数据。在内部循环中,尝试在变量中缓存重复的表达式。并用于+=避免在添加元素时两次评估数组表达式。

$recs_assoc = array();
foreach ($recs as $r) {
    $recs_assoc[$r[0]] = $r[1];
}
$authpts = array();
foreach ($obj["pro"] as $key => $val) {
    $wr = $recs_assoc[$key];
    $c_val = count($val);
    for ($i=0; $i<$c_val; $i++) {
        $thisval = $val[$i];
        $authid = $thisval["authid"];
        if (!array_key_exists($authid, $authpts)) {
            $authpts[$authid] = 0;
        }
        $ratio = 0;
        if (strlen($c_wr) > 0) {
            $ratio = comparetime($thisval["time"], $wr);
            $ratio = $ratio[0];
        }
        $rbonus = ($ratio > 0) ? pow($ratio, (2 / $ratio)) : 0;
        $authpts[$authid] += ($c_val - $i) * (1 + $rbonus);
    }
}

如果您将array_key_exists最后一个分配更改为:

        @$authpts[$authid] += ($c_val - $i) * (1 + $rbonus);

@抑制通常由增加不存在的元素引起的警告。它会将元素视为包含 0,因此仍会获得正确的结果。

于 2013-09-13T20:18:32.313 回答