Php 提高查询运行时间(加载页面需要20秒以上)

Php 提高查询运行时间(加载页面需要20秒以上),php,mysql,sql,mysqli,Php,Mysql,Sql,Mysqli,我有一个查询,每次用户打开他的个人资料页面时都会加载。 它真的很慢。加载页面需要20秒以上的时间。 这是一个很简单的查询,但是有很多行,所以看它时不要害怕 我希望在改进我的查询方面能得到任何帮助 SELECT `h`.`login` AS `login`, SUM(IF(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),`h`.`pips`,NULL)) AS `total_pips`, COUNT(IF(((`h`.`cmd` = 0) OR

我有一个查询,每次用户打开他的个人资料页面时都会加载。 它真的很慢。加载页面需要20秒以上的时间。 这是一个很简单的查询,但是有很多行,所以看它时不要害怕

我希望在改进我的查询方面能得到任何帮助

SELECT 
    `h`.`login` AS `login`,
    SUM(IF(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),`h`.`pips`,NULL)) AS `total_pips`,
    COUNT(IF(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),`h`.`position_num`,NULL)) AS `total_trades`,
    (COUNT(IF(((`h`.`pl` > 0) AND ((`h`.`cmd` = 0) OR (`h`.`cmd` = 1))),`h`.`pl`,NULL)) / COUNT(IF(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),`h`.`position_num`,NULL))) AS `winning_trades_percent`,
    SUM(if(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),`h`.`gain`,NULL)) AS `total_gain`,
    (SELECT AVG(`wg`.`weekly_gain_all`) FROM `gt_view_weekly_gain` `wg` where (`wg`.`login` = `h`.`login`) group by `wg`.`login`) AS `weekly_gain`,
    AVG(IF(((`h`.`pips` > 0) AND ((`h`.`cmd` = 0) OR (`h`.`cmd` = 1))),`h`.`pips`,NULL)) AS `average_profit_pips`,
    AVG(IF(((`h`.`pips` <= 0) AND ((`h`.`cmd` = 0) OR (`h`.`cmd` = 1))),`h`.`pips`,NULL)) AS `average_lose_pips`,
    AVG(IF(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),`h`.`pips`,NULL)) AS `average_pips`,
    AVG(time_to_sec(IF(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),timediff(`h`.`close_time`,`h`.`open_time`),NULL))) AS `average_trade_time`,
    STD(IF(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),`h`.`pips`,NULL)) AS `volatility`,
    MAX(IF(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),`h`.`pips`,NULL)) AS `best_trade`,
    MIN(IF(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),`h`.`pips`,NULL)) AS `worst_trade`,
    (ceiling(((ceiling(to_days(now())) - ceiling(to_days(MIN(IF(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),`h`.`open_time`,NULL))))) / 7)) - 1) AS `running_weeks`,
    (SELECT `fn`.`followers_num_all` FROM `gt_view_followers_num` `fn` where ((`fn`.`guru_id` = `h`.`guru_or_guru_user_id`) AND (`h`.`is_guru_history` = 1))) AS `followers_num`,
    SUM(IF(((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)),`h`.`pl`,NULL)) AS `total_profit_loss`,
    SUM(IF(((`h`.`cmd` = 6) AND (`h`.`pl` > 0)),`h`.`pl`,NULL)) AS `deposits`,
    SUM(IF(((`h`.`cmd` = 6) AND (`h`.`pl` < 0)),`h`.`pl`,NULL)) AS `withdrawls`,
    COUNT(IF((((`h`.`cmd` = 0) OR (`h`.`cmd` = 1)) AND (`h`.`pl` > 0)),`h`.`position_num`,NULL)) AS `total_winning_trades_count`,
    ABS((AVG(IF(((`h`.`pips` > 0) AND ((`h`.`cmd` = 0) OR (`h`.`cmd` = 1))),`h`.`pips`,NULL)) / AVG(IF(((`h`.`pips` <= 0) AND ((`h`.`cmd` = 0) OR (`h`.`cmd` = 1))),`h`.`pips`,NULL)))) AS `average_profit_loss_ratio` 
FROM 
    `gt_history` `h` 
WHERE
    `h`.`is_closed` = 1
GROUP BY
    `h`.`login`

这个查询似乎计算了所有用户的值。如果您希望仅为一个用户显示此内容,那么在where子句中添加并登录class='xxx'可能会快得多


否则,正如Mihai所建议的,缓存可能是最好的方法。

如果尝试在where子句中过滤它,则不要在每列中使用h.cmd=0或h.cmd=1。它可能会有所改进,因为数据选择减少。

此查询无法读取,为什么不缓存响应,并且仅在用户更改某些内容或每天刷新一次时才刷新缓存?感谢您的“e”响应:。我已经使它尽可能可读,每一行代表一行。这是一个简单的和/如果/计数。我认为问题来自select语句。你知道我该如何改进它吗?你能告诉我哪些表提供了你所拥有的数据模式以及你想做什么吗?我认为这会使给你一个好的答案变得更容易。你建议怎么做?你正在用NULL来抑制h.cmd的所有其他值。您只考虑H.CMD=0或H.CMD=1。因此,如果在where子句中使用它会更好,其中h.is_closed=1和h.cmd=0或h.cmd=1。谢谢!:它将查询时间从20秒提高到2秒。