Witaj Gościu! ( Zaloguj | Rejestruj )

Forum PHP.pl

 
Reply to this topicStart new topic
> [MySQL][PHP] Tagi - struktura bazy danych i pobieranie kilku wartości
arek33
post 17.04.2011, 15:35:36
Post #1





Grupa: Zarejestrowani
Postów: 72
Pomógł: 0
Dołączył: 24.02.2009

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


Witam ponownie,
Przeczesałem wczoraj połowę internetu, ale problem nadal jest na podobnym poziomie na jakim był przed rozpoczęciem poszukiwań. Sprawa dotyczy się systemu dodawania newsów i słów kluczowych (tagów).

Struktura bazy wyglądać będzie następująco(?):

news:
- id_news
- tytul
- tresc
- data
- autor
- id_tags (?)

tagi:
- id_tags
- tag

tagi_news
- id_tags (int?)
- id_news

Proszę o kompetentną osobę czy powyższa struktura jest prawidłowa czy może warto coś dodać/zmienić?

Przykład wyświetlania artykułu (news):
Tytuł: Nowy wpis
Treść: Lorem ipsum...
Data: Dzisiaj o 19:11
Autor: Admin
Tagi: nowy wpis, lorem ipsum, lorem

Jak widać w powyższym przykładzie chcę użyć 3+ słów kluczowych, niemniej jednak nie wiem jak się za to zabrać.

Ad1. Przede wszystkim zależy mi na opinii czy struktura bazy danych jest odpowiednia?
Ad2. Mając przypisane:

id_tags = 1
tag = nowy wpis

id_tags = 2
tag = lorem ipsum

id_tags = 3
tag = lorem

Jak wpisać wszystkie 3 do id_tags z tabeli news? Rozumiem, że relacja zachodząca pomiędzy tabelami to jeden do wielu, niemniej jednak nadal nie mam odpowiednich wskazówek do satysfakcjonującego mnie rozwiązania. Z góry dziękuję za pomoc, linki do artykułów, które będą mi w stanie pomóc oraz pozostałe cenne wskazówki.

Arek
Go to the top of the page
+Quote Post
dziamber
post 17.04.2011, 16:39:36
Post #2





Grupa: Zarejestrowani
Postów: 57
Pomógł: 18
Dołączył: 15.04.2009
Skąd: Kwidzyn

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


Ja bym zrobił to tak:

  1. news:
  2. - id_news
  3. - tytul
  4. - tresc
  5. - DATA
  6. - autor
  7. - tags


  1. tags:
  2. - id
  3. - nazwa


I np. jak masz trzy tagi w newsie to trzymasz ich id oddzielone przecinkami, a jak chcesz je wyciągnąć to coś w stylu:

  1. # pobierasz dane z bazy
  2. $tagi = $dane_z_bazy->tags;
  3. $tagi = explode(",", $tagi);
  4. $ile_tagow = count($tagi);
  5. $jest = 0;
  6. while($jest <= $ile_tagow) {
  7. echo $tagi[$jest];
  8. $jest++;
  9. }
Go to the top of the page
+Quote Post
Bags_Bunny
post 17.04.2011, 16:41:46
Post #3





Grupa: Zarejestrowani
Postów: 262
Pomógł: 39
Dołączył: 12.04.2004

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


Orl korrect! Mam podobną sytuację z użytkownikami w Kohanie. Jest tabela user z danymi użytkowników (u Ciebie nowości), tabela z rolami tychże (odpowiednik Twoich tagów) oraz tabela z przypisaniami zwana role_user, czyli odpowiednik Twojego tagi_news.

Załóżmy, iż chcę wybrać id użytkownika, jego pierwsze imię, a także jego role w postaci id_roli:nazwa_roli;id_roli:nazwa_roli;...
Co więcej, chcę aby ta lista była posortowana w/g nazwy roli, a całość wyników w/g imienia.

Mogę to zrobić na przykład następującym zapytaniem:
  1. SELECT u.user_id, u.first_name, GROUP_CONCAT( DISTINCT CONCAT(r.role_id, ":", r.name) ORDER BY r.name ASC SEPARATOR ";" ) roles FROM user u NATURAL JOIN role_user ru NATURAL JOIN role r GROUP BY user_id ORDER BY u.first_name

Dla jasności dodałem wszędzie nazwę tabeli.

--edit--
Dla ułatwienia wrzucam jeszcze strukturę:
  1. --
  2. -- Table structure for table `role`
  3. --
  4.  
  5. CREATE TABLE `role` (
  6. `role_id` int(10) UNSIGNED NOT NULL AUTO_INCREMENT,
  7. `name` varchar(32) NOT NULL,
  8. `description` varchar(255) NOT NULL,
  9. PRIMARY KEY (`role_id`),
  10. UNIQUE KEY `uniq_name` (`name`)
  11. ) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=3 ;
  12.  
  13. -- --------------------------------------------------------
  14.  
  15. --
  16. -- Table structure for table `role_user`
  17. --
  18.  
  19. CREATE TABLE `role_user` (
  20. `user_id` int(10) UNSIGNED NOT NULL,
  21. `role_id` int(10) UNSIGNED NOT NULL,
  22. PRIMARY KEY (`user_id`,`role_id`)
  23. ) ENGINE=MyISAM DEFAULT CHARSET=utf8;
  24.  
  25. -- --------------------------------------------------------
  26.  
  27. --
  28. -- Table structure for table `user`
  29. --
  30.  
  31. CREATE TABLE `user` (
  32. `user_id` int(10) UNSIGNED NOT NULL AUTO_INCREMENT,
  33. `created_at` int(16) UNSIGNED NOT NULL,
  34. `updated_at` int(16) UNSIGNED DEFAULT NULL,
  35. `password` varchar(64) NOT NULL,
  36. `first_name` varchar(16) NOT NULL,
  37. `email` varchar(64) NOT NULL,
  38. `logins` int(10) UNSIGNED NOT NULL DEFAULT '0',
  39. `last_login` int(10) UNSIGNED DEFAULT NULL,
  40. `deleted` int(1) UNSIGNED NOT NULL DEFAULT '0',
  41. PRIMARY KEY (`user_id`),
  42. UNIQUE KEY `email_UNIQUE` (`email`)
  43. ) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=13 ;


--edit--
Jeszcze drobne uwagi kosmetyczne:
Weź pod uwagę, że DISTINCT jest akurat w tym przypadku zbędny, bo wszystko ma klucze. Napisałem z rozpędu wink.gif.
Ponadto, u Ciebie zapewne LEFT JOIN sprawdzi się bardziej niż NATURAL JOIN, który użyłem tutaj dla przejrzystości zapytania.

Ten post edytował Bags_Bunny 17.04.2011, 16:49:31


--------------------
rm -rf /*
Go to the top of the page
+Quote Post
arek33
post 17.04.2011, 23:44:34
Post #4





Grupa: Zarejestrowani
Postów: 72
Pomógł: 0
Dołączył: 24.02.2009

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


Dzięki Panowie za pomoc! Rozwiązałem to nieco inaczej, ale te dwie riposty nakierowały mnie odpowiednio - jestem zadowolony z rezultatu. Ostatnie chyba pytanie mam - jaką funkcją w PHP dobiorę się do ostatniego wyniku pobranego z bazy danych za pośrednictwem pętli while? Wyrzucam moje tagi: 123, abc, zxc, cxz, itp.

  1. echo "".$r['id_newsa'].", ";


I jak wiadomo wynik mój będzie wyglądał następująco: tag1, tag2, tag3, [przecinek na końcu], w jaki sposób mogę się go pozbyć?

Cytat(arek33 @ 18.04.2011, 00:15:49 ) *
Dzięki Panowie za pomoc! Rozwiązałem to nieco inaczej, ale te dwie riposty nakierowały mnie odpowiednio - jestem zadowolony z rezultatu. Ostatnie chyba pytanie mam - jaką funkcją w PHP dobiorę się do ostatniego wyniku pobranego z bazy danych za pośrednictwem pętli while? Wyrzucam moje tagi: 123, abc, zxc, cxz, itp.

  1. echo "".$r['id_newsa'].", ";


I jak wiadomo wynik mój będzie wyglądał następująco: tag1, tag2, tag3, [przecinek na końcu], w jaki sposób mogę się go pozbyć?

Gdyby kogoś to interesowało to rozwiązałem to w następujący sposób:

  1. if($mnr <= $r['id_newsa']){
  2.  
  3. echo "".$r['id_newsa']."";
  4. }
  5. else{
  6.  
  7. echo "".$r['id_newsa'].", ";
  8.  
  9. }
  10. // gdzie $mnr = mysql_num_rows($wynik)
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: 18.05.2025 - 09:17