Witaj Gościu! ( Zaloguj | Rejestruj )

Forum PHP.pl

> Zliczanie unikalnych wartości, Optymalizacja
snapshot
post 24.05.2011, 10:46:51
Post #1





Grupa: Zarejestrowani
Postów: 96
Pomógł: 6
Dołączył: 22.08.2007
Skąd: Wrocław

Ostrzeżenie: (0%)
-----


Chcę wyciągnąć ilość unikalnych osób, które głosowały. Zakładamy, że użytkownik może głosować kilka razy.
  1. SELECT COUNT(DISTINCT user) FROM vote WHERE type = 5

Powyższe zapytanie działa tak jak chcę, jednak czas wykonywania jest nie do zaakceptowania i wynosi 0.8-1.0 sekundy. Dodam, że tabela posiada aktualnie około 600 000 rekordów. Da się szybciej? smile.gif


--------------------
ZF developer
Go to the top of the page
+Quote Post
 
Start new topic
Odpowiedzi (1 - 8)
nospor
post 24.05.2011, 10:50:38
Post #2





Grupa: Moderatorzy
Postów: 36 557
Pomógł: 6315
Dołączył: 27.12.2004




a masz założony index na type?


--------------------

"Myśl, myśl, myśl..." - Kubuś Puchatek || "Manual, manual, manual..." - Kubuś Programista
"Szukaj, szukaj, szukaj..." - Kubuś Odkrywca || "Debuguj, debuguj, debuguj..." - Kubuś Developer

Go to the top of the page
+Quote Post
Crozin
post 24.05.2011, 10:51:28
Post #3





Grupa: Zarejestrowani
Postów: 6 476
Pomógł: 1306
Dołączył: 6.08.2006
Skąd: Kraków

Ostrzeżenie: (0%)
-----


Zapewne masz jakąś tabelę która reprezentuje sondę na którą mogą głosować użytkownicy, tak? Dodaj do niej dwie kolumny total_votes oraz total_unique_votes. Następnie dodaj sobie wyzwalacz, który po dodaniu rekordu do tabeli vote zwiększy wartości obu kolumn i analogicznie przy usunięciu zmniejszy je. Dzięki temu w ogóle nie będziesz musiał dynamicznie zliczać tych głosów.

EDIT: Dopiero teraz zauważyłem "type = 5" - w takim razie raczej powyższe będzie bezużyteczne.

Ten post edytował Crozin 24.05.2011, 10:52:14
Go to the top of the page
+Quote Post
wookieb
post 24.05.2011, 10:51:29
Post #4





Grupa: Moderatorzy
Postów: 8 989
Pomógł: 1550
Dołączył: 8.08.2008
Skąd: Słupsk/Gdańsk




Jak już to na type, user (2 kolumny w jednym indeksie)


--------------------
Go to the top of the page
+Quote Post
snapshot
post 24.05.2011, 11:35:02
Post #5





Grupa: Zarejestrowani
Postów: 96
Pomógł: 6
Dołączył: 22.08.2007
Skąd: Wrocław

Ostrzeżenie: (0%)
-----


Wpadłem na to sam @wookieb i faktycznie działa. Mam teraz 0.02. Dzięki. Jednak mam kolejny problem. Muszę podczas realizacji innego scenariusza (unikalne grupy) podłączyć inną tabelę:
  1. SELECT COUNT(DISTINCT u.team) FROM vote v INNER JOIN user u USING(user) WHERE v.type = 5

Czas wykonywania to znowu ~1 sekundy. Analogicznie dodałbym index na dwóch kolumnach w dwóch różnych tabelach, ale chyba się nie da...

Ten post edytował snapshot 24.05.2011, 11:36:50


--------------------
ZF developer
Go to the top of the page
+Quote Post
wookieb
post 24.05.2011, 11:38:31
Post #6





Grupa: Moderatorzy
Postów: 8 989
Pomógł: 1550
Dołączył: 8.08.2008
Skąd: Słupsk/Gdańsk




Tabela user ma index na "user"?
user to login czy id usera? Jezeli login to zacznij używać id.
Silnik tabel polecam ustawić na INNODB.


--------------------
Go to the top of the page
+Quote Post
snapshot
post 24.05.2011, 11:45:25
Post #7





Grupa: Zarejestrowani
Postów: 96
Pomógł: 6
Dołączył: 22.08.2007
Skąd: Wrocław

Ostrzeżenie: (0%)
-----


Kolumna user w tabli user to int Primary key. Silnik InnoDB


--------------------
ZF developer
Go to the top of the page
+Quote Post
wookieb
post 24.05.2011, 11:47:41
Post #8





Grupa: Moderatorzy
Postów: 8 989
Pomógł: 1550
Dołączył: 8.08.2008
Skąd: Słupsk/Gdańsk




Wrzuć prosze explain z zapytania
  1. EXPLAIN twoj_select

oraz schematy tabel user,vote
  1. SHOW CREATE TABLE `user`;
  2. SHOW CREATE TABLE `vote`';


--------------------
Go to the top of the page
+Quote Post
snapshot
post 24.05.2011, 12:36:48
Post #9





Grupa: Zarejestrowani
Postów: 96
Pomógł: 6
Dołączył: 22.08.2007
Skąd: Wrocław

Ostrzeżenie: (0%)
-----


Dla poprzenich przykładów zmieniałem nazwy tabeli, żeby można było się połapać. Teraz pozwolę sobie zostawić oryginały.
  1. EXPLAIN SELECT COUNT(DISTINCT s.idartist) FROM on_air o INNER JOIN song s USING(idsong) WHERE o.idradio = 5

Kod
+----+-------------+-------+--------+------------------------------------------------+---------------------+---------+----------------+-------+-------+
| id | select_type | table | type   | possible_keys                                  | key                 | key_len | ref            | rows  | Extra |
+----+-------------+-------+--------+------------------------------------------------+---------------------+---------+----------------+-------+-------
|  1 | SIMPLE      | o     | ref    | fk_Onair_Radio1_idx,fk_Onair_Song1_idx,idradio | fk_Onair_Radio1_idx | 1       | const          | 49470 |       |
|  1 | SIMPLE      | s     | eq_ref | PRIMARY                                        | PRIMARY             | 3       | radio.o.idsong |     1 |       |
+----+-------------+-------+--------+------------------------------------------------+---------------------+---------+----------------+-------+-------+
2 rows in set (0.14 sec)

  1. CREATE TABLE `song` (
  2. `idsong` mediumint(8) UNSIGNED NOT NULL AUTO_INCREMENT,
  3. `title` varchar(50) COLLATE utf8_unicode_ci NOT NULL,
  4. `redirect` mediumint(8) UNSIGNED DEFAULT NULL,
  5. `img_small` varchar(255) COLLATE utf8_unicode_ci DEFAULT NULL,
  6. `img_big` varchar(255) COLLATE utf8_unicode_ci DEFAULT NULL,
  7. `description` mediumblob,
  8. `lyric` mediumblob,
  9. `youtube` varchar(33) COLLATE utf8_unicode_ci DEFAULT NULL,
  10. `last_data_check` date NOT NULL,
  11. `idartist` mediumint(8) UNSIGNED NOT NULL,
  12. `slug` varchar(50) COLLATE utf8_unicode_ci NOT NULL,
  13. PRIMARY KEY (`idsong`),
  14. UNIQUE KEY `un_Song_title_idArtist_idx` (`title`,`idartist`),
  15. UNIQUE KEY `IN_Song_slug_idx` (`slug`),
  16. KEY `fk_Song_Artist_idx` (`idartist`),
  17. KEY `reditect_idx` (`redirect`),
  18. CONSTRAINT `song_idartist_artist_idartist` FOREIGN KEY (`idartist`) REFERENCES `artist` (`idartist`) ON DELETE CASCADE ON UPDATE CASCADE,
  19. CONSTRAINT `song_redirect_song_idsong` FOREIGN KEY (`redirect`) REFERENCES `song` (`idsong`) ON DELETE SET NULL ON UPDATE SET NULL
  20. ) ENGINE=InnoDB AUTO_INCREMENT=25692 DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci

  1. CREATE TABLE `on_air` (
  2. `idonair` mediumint(8) UNSIGNED NOT NULL AUTO_INCREMENT,
  3. `time` datetime NOT NULL,
  4. `idradio` tinyint(3) UNSIGNED NOT NULL,
  5. `idsong` mediumint(8) UNSIGNED NOT NULL,
  6. PRIMARY KEY (`idonair`),
  7. KEY `fk_Onair_Radio1_idx` (`idradio`),
  8. KEY `fk_Onair_Song1_idx` (`idsong`),
  9. KEY `idradio` (`idradio`,`idsong`),
  10. CONSTRAINT `on_air_idradio_radio_idradio` FOREIGN KEY (`idradio`) REFERENCES `radio` (`idradio`) ON DELETE CASCADE ON UPDATE CASCADE,
  11. CONSTRAINT `on_air_idsong_song_idsong` FOREIGN KEY (`idsong`) REFERENCES `song` (`idsong`) ON DELETE CASCADE ON UPDATE CASCADE
  12. ) ENGINE=InnoDB AUTO_INCREMENT=639365 DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci


--------------------
ZF developer
Go to the top of the page
+Quote Post

Reply to this topicStart new topic
1 Użytkowników czyta ten temat (1 Gości i 0 Anonimowych użytkowników)
0 Zarejestrowanych:

 



RSS Wersja Lo-Fi Aktualny czas: 19.07.2025 - 05:44