MySQL查询 - 替代方案

时间:2014-09-01 09:08:51

标签: php mysql sql

我的查询太长(3-4s)。任何想法是如何使这更快?

SELECT u.id AS id_uzytkownika,
       u.login,
       u.ranga,
       u.online_light AS online,

  (SELECT MAX(id)
   FROM uzytkownicy_zdjecia
   WHERE id_uzytkownika = u.id
     AND prywatna =0) AS id_fotki,

  (SELECT fotka
   FROM uzytkownicy_zdjecia
   WHERE id = id_fotki) AS fotka ,

  (SELECT srednia_ocen
   FROM uzytkownicy_zdjecia
   WHERE id = id_fotki) AS srednia_ocen,

  (SELECT ile_ocen
   FROM uzytkownicy_zdjecia
   WHERE id = id_fotki) AS ile_ocen
FROM uzytkownicy u
WHERE u.foto =1
  AND u.plec = "mezczyzna"
ORDER BY srednia_ocen DESC,
         ile_ocen DESC,
         id_fotki DESC LIMIT 42

3 个答案:

答案 0 :(得分:0)

您可以解释一下您的表格结构以及此查询的内容吗?由于列名不是英文,大多数读者可能会有一个问题,你在这里想要做什么......

一般来说,看起来你在同一张表中有很多嵌套的SELECTS - 有什么特别的原因吗?

答案 1 :(得分:0)

试试这个:

SELECT u.id AS id_uzytkownika,
   u.login,
   u.ranga,
   u.online_light AS online,

(SELECT MAX(id)
FROM uzytkownicy_zdjecia
WHERE id_uzytkownika = u.id
 AND prywatna =0) AS id_fotki,
z.fotka, 
z.srednia_ocen,
z.ile_ocen
FROM uzytkownicy u
JOIN uzytkownicy_zdjecia z
ON u.id_fotki = z.id
WHERE u.foto =1
  AND u.plec = "mezczyzna"
ORDER BY srednia_ocen DESC,
     ile_ocen DESC,
     id_fotki DESC LIMIT 42

我用JOIN替换了3个子查询。第一个子查询具有不同的条件,如果您可以将该条件与其他查询合并,则可以将其删除。

注意您已将id_fokta命名为子查询的结果,但同名的主键为uzytkownicy表

答案 2 :(得分:0)

您不必一次又一次地使用相同的标准查询同一个表。使用简单连接替换您的子选择。 LEFT JOIN,如果可能没有匹配的记录。

SELECT 
  u.id AS id_uzytkownika,
  u.login,
  u.ranga,
  u.online_light AS online,
  (
    SELECT MAX(id)
    FROM uzytkownicy_zdjecia
    WHERE id_uzytkownika = u.id
    AND prywatna =0
  ) AS id_fotki,
  uz.fotka,
  uz.srednia_ocen,
  uz.ile_ocen
FROM uzytkownicy u
LEFT JOIN uzytkownicy_zdjecia uz ON uz.id = u.id_fotki
WHERE u.foto = 1
  AND u.plec = "mezczyzna"
ORDER BY u.srednia_ocen DESC,
         u.ile_ocen DESC,
         u.id_fotki DESC LIMIT 42

编写上述查询的另一种方法是首先聚合然后加入:

SELECT 
  u.id AS id_uzytkownika,
  u.login,
  u.ranga,
  u.online_light AS online,
  uzz.id_fotki,
  uz.fotka,
  uz.srednia_ocen,
  uz.ile_ocen
FROM uzytkownicy u
LEFT JOIN uzytkownicy_zdjecia uz ON uz.id = u.id_fotki
LEFT JOIN
(
  SELECT id_uzytkownika, MAX(id) AS id_fotki
  FROM uzytkownicy_zdjecia
  WHERE prywatna =0
  GROUP BY id_uzytkownika
) uzz ON uzz.id_uzytkownika = u.id
WHERE u.foto = 1
  AND u.plec = "mezczyzna"
ORDER BY u.srednia_ocen DESC,
         u.ile_ocen DESC,
         u.id_fotki DESC LIMIT 42

顺便说一句:什么是" mezczyzna"?一串?那么这应该是单引号。