【问题标题】:Why is this php script running so slow (Simple select) [closed]为什么这个 php 脚本运行这么慢(简单选择)[关闭]
【发布时间】:2016-08-02 18:38:26
【问题描述】:

当我在 google chrome 中尝试使用脚本 URL 时,该脚本运行非常缓慢,我想知道原因:

<?php

    include 'config.php';

    $conn = mysqli_connect($servername, $username, $password, $dbname);

    $playerEmail = $_REQUEST["playerEmail"];

    $sql = "SELECT *
        FROM players
        WHERE EMAIL = '$playerEmail'";

    $res = mysqli_query($conn,$sql);

    $result = array();

    while($row = mysqli_fetch_array($res)){
        array_push($result,
        array('EMAIL'=>$row[0],
              'DATEOFSIGNUP'=>$row[2],
              'USERNAME'=>$row[3],
              'GENDER'=>$row[4],
              'JOB'=>$row[5],
              'LVL'=>$row[6],
              'HP_NOW'=>$row[7],
              'HP_MAX'=>$row[8],
              'MANA_NOW'=>$row[9],
              'MANA_MAX'=>$row[10],
              'STR'=>$row[11],
              'SPD'=>$row[12],
              'INTEL'=>$row[13],
              'XP_NOW'=>$row[14],
              'XP_NEEDED'=>$row[15],
              'GOLDS'=>$row[16],
              'NUMBERSOFITEMS'=>$row[17],
              'LOCATION_X'=>$row[18],
              'LOCATION_Y'=>$row[19]
              ));
    }

    echo json_encode(array("result"=>$result));

    mysqli_close($conn);

?>

我所有的其他脚本都是使用 $_REQUEST 制作的,所以我不相信这是原因。任何你能想到的,随时在这里分享。

非常感谢大家!

【问题讨论】:

  • 哪个部分运行缓慢?你做过基准测试吗?
  • 您的查询返回大约多少行?
  • 这似乎过于复杂了;为什么不直接从数据库中返回一个关联数组呢?如果你使用 PDO,你甚至可以使用 fetchAll 来完全省去循环。
  • 通过使用select *,您可能会提取不必要的数据;仅仅因为您实际上没有使用它并不意味着它不会被发送。现在想象一下,如果有人稍后将玩家照片(作为 BLOB)直接添加到表中,这可能会慢得多。

标签: php mysql database select


【解决方案1】:

您需要有一个索引 om you EMAIL 列以保持速度。

$sql = "SELECT *
    FROM players
    WHERE EMAIL = '$playerEmail'";

创建索引:

CREATE INDEX idx_nn_1 ON players(EMAIL);

由于您的代码对使用 SQL 注入的任何人开放,因此请阅读 SQL 注入和 PHP PDO。你的代码甚至是 SQL 注入最容易破解的代码之一(所以真的要让这段代码更好,否则你就有麻烦了)。

【讨论】:

  • 我可以为你做这件事提醒用户注意安全风险很好,但建议使用它们并不具有建设性。
  • @A.L 用一些幽默来表达观点......
  • @NorbertvanNobelen,索引推荐 +1。我也支持警告人们注意安全风险,我支持使用幽默,但讽刺通常很难让读者在纯文本媒体中识别。
  • @BillKarwin 删除了讽刺 :)
【解决方案2】:

在您的 EMAIL 列上创建索引的答案是正确的,但为了将来参考,这里有一个更快、更安全的方法来使用 PDO 进行编码:

<?php

include 'config.php';

try {
    $pdo = new PDO("mysql:host=$servername;dbname=$dbname",
        $username, $password, [PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION]);
} catch (PDOException $e) {
    error_log("PDO connection failed in " . __FILE__ . 
        ", Error: " . $e->getMessage());
    die("Database error, please contact administrator");
}

$playerEmail = $_REQUEST["playerEmail"];

$sql = "SELECT EMAIL, DATEOFSIGNUP, USERNAME, GENDER,
          JOB, LVL, HP_NOW, HP_MAX, MANA_NOW, MANA_MAX,
          STR, SPD, INTEL, XP_NOW, XP_NEEDED, GOLDS,
          NUMBERSOFITEMS, LOCATION_X, LOCATION_Y
    FROM players
    WHERE EMAIL = ?";

$stmt = $pdo->prepare($sql);
$stmt->execute([$playerEmail]);

$result = $stmt->fetchAll(PDO::FETCH_ASSOC);

echo json_encode(array("result"=>$result));

【讨论】:

    猜你喜欢
    • 2011-01-18
    • 2018-10-08
    • 1970-01-01
    • 2012-06-13
    • 1970-01-01
    • 2019-07-02
    • 2011-10-18
    • 2019-05-02
    • 1970-01-01
    相关资源
    最近更新 更多