Witaj Gościu! ( Zaloguj | Rejestruj )

Forum PHP.pl

 
Reply to this topicStart new topic
> Zamian danych w tabeli między dwoma rekordami
fbi
post 19.04.2018, 00:28:51
Post #1





Grupa: Zarejestrowani
Postów: 6
Pomógł: 0
Dołączył: 6.10.2009

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


Witam,

Otóż mam tabelę kursy która zawiera pola id, id_kierowcy, trasa, data, godzina, uwagi ; (pole id_kierowcy jest UNIQUE - czyli nie możne się powtarzać ). W tabeli przykładowo są:

| ID | ID_KIEROWCY |TRASA | DATA | GODZINA | UWAGI |
---------------------------------------------------------------------
| 1 | 23 |EŁK | 23.04| 14:00 | |
---------------------------------------------------------------------
| 2 | 12 |POZNAN |12.05 | 12:30 | |
---------------------------------------------------------------------

Jak prostym zapytaniem wykonać wymianę kierowców, aby kierowca id 23 miał trasę 2 , a drugi trasę 1 , zaznaczam ze pole id_kierowcy jest UNIQUE

Pozdrawiam
Go to the top of the page
+Quote Post
Tomplus
post 19.04.2018, 02:56:48
Post #2





Grupa: Zarejestrowani
Postów: 1 216
Pomógł: 142
Dołączył: 20.03.2005
Skąd: Będzin

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


Myślę to unique dla id_kierowcy to błąd.

Co wtedy gdy jeden kierowca będzie miał dwie trasy? Bo widzę że umieszczasz daty, więc przy różnych trasach nawet w czasie będą się kierowcy wymieniać.
23.04 będzie kierowca 23, ale za miesiąc 23.05, może to być już kierowca 124, a nie 23, a 23 będzie miał trasą do Sosnowca albo Radomia smile.gif
Go to the top of the page
+Quote Post
mmmmmmm
post 19.04.2018, 07:23:29
Post #3





Grupa: Zarejestrowani
Postów: 1 386
Pomógł: 302
Dołączył: 18.04.2012

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


  1. UPDATE kursy SET id_kierowcy=35-id_kierowcy WHERE id_kierowcy IN (23,12) -- to 35 to suma tych id
Go to the top of the page
+Quote Post
Pyton_000
post 19.04.2018, 07:57:16
Post #4





Grupa: Zarejestrowani
Postów: 7 378
Pomógł: 1304
Dołączył: 26.10.2005

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


@m to raczej nie zadziała bo sprawdzanie kluczy jest po update każdego wiersza więc już 1-szy update się nie powiedzie.

Tu jest rozwiązanie używając transakcji: https://stackoverflow.com/a/11207946
Go to the top of the page
+Quote Post
Lukeup
post 19.04.2018, 08:40:11
Post #5





Grupa: Zarejestrowani
Postów: 20
Pomógł: 5
Dołączył: 13.04.2018

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


Porada @mmmmmmm niestety nie zadziała, ze względu na UNIQUE. Możesz:
1. Transakcje (@Pyton_000) - według mnie, najlepsze rozwiązanie.
2. Zamienić jedno id_kierowcy na jakieś inne, tymczasowe, które jeszcze nie występuje w bazie, zmienić to drugie id, na to, którego oczekujesz (wtedy jest już wolne) i finalnie na podstawie tymczasowego id zamienić w drugim miejscu (i znowu będzie już wolne, przykładowo 12, bo zmieniłeś już 12 na 23). Można też utworzyć jakąś tymczasową tabelę właśnie na taką operację i przechowywać w niej tymczasowe id.
3. Usunąć UNIQUE (DROP INDEX...), w zależności od potrzeby dodać:
  1. SET SQL_SAFE_UPDATES = 0;

(wtedy nie jest wymagana kolumna-klucz), wykonać zapytanie (@mmmmmmm) i potem przywrócić UNIQUE, eg.
  1. ADD UNIQUE INDEX `id_kierowcy_UNIQUE` (`id_kierowcy` ASC);

i w zależności od potrzeb, przywrócić bezpieczne aktualizacje:
  1. SET SQL_SAFE_UPDATES = 1;
Go to the top of the page
+Quote Post
Pyton_000
post 19.04.2018, 08:41:59
Post #6





Grupa: Zarejestrowani
Postów: 7 378
Pomógł: 1304
Dołączył: 26.10.2005

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


Wywalanie kluczy i dodawanie ich na nowo to nie jest za dobry pomysł wink.gif Wyobraź sobie tabel która ma powiedzmy 100GB danych wink.gif Mówimy o przypadku zmiany takiej trywialnej. Bo jeślibyśmy zmieniali dużo wartości to wtedy warto to rozważyć bo update pójdzie dość szybko a indeks się odbuduje tylko 1x

Ten post edytował Pyton_000 19.04.2018, 08:42:59
Go to the top of the page
+Quote Post
fbi
post 19.04.2018, 09:39:47
Post #7





Grupa: Zarejestrowani
Postów: 6
Pomógł: 0
Dołączył: 6.10.2009

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


Dziękuje za zainteresowanie,

Dlaczego UNIQUE id_kierowcy , nie che dopuścić aby na trasie było dwóch kierowców, a trasy są w czasie teraźniejszym,

Pierwszy raz słyszę o TRANSACTION sad.gif

  1. START TRANSACTION ;
  2. UPDATE kursy
  3. SET id_kierowcy=
  4. CASE
  5. WHEN id_kierowcy= 2 THEN -3
  6. WHEN id_kierowcy= 3 THEN -2
  7. END
  8. WHERE id_kierowcy IN (2,3) ;
  9.  
  10. UPDATE kursy
  11. SET id_kierowcy= - id_kierowcy
  12. WHERE id_kierowcy IN (-2,-3) ;
  13. COMMIT ;


Moża poprosić o wyśnienie co oznaczają liczby ujemne ,
Go to the top of the page
+Quote Post
Pyton_000
post 19.04.2018, 09:45:11
Post #8





Grupa: Zarejestrowani
Postów: 7 378
Pomógł: 1304
Dołączył: 26.10.2005

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


ustawia Ci po prostu ID na np. -12 a potem po zamianie obu na liczby ujemne robi odwrócenie.

Tylko jedna uwaga. `id_kierowcy` nie może być unsigned bo to nie zadziała (czyliu musi zezwalać na wpisanie do kolumny liczby ujemnej)
Go to the top of the page
+Quote Post
Tomplus
post 19.04.2018, 11:30:37
Post #9





Grupa: Zarejestrowani
Postów: 1 216
Pomógł: 142
Dołączył: 20.03.2005
Skąd: Będzin

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


@fbi
Ale na trasie nie mogą być w tym samym czasie, a nie w różnych trasach.
I co wtedy gdy masz kierowców na długie trasy gdzie muszą się wymieniać. Wtedy na taką trasę zatrudnia się więcej niż 1 kierowcę.

Lepiej będzie wysłać zapytanie sprawdzające czy dany kierowca podczas dodawania do trasy nie jest już przypisany do jakiejś trasy.
Go to the top of the page
+Quote Post
Lukeup
post 19.04.2018, 16:23:29
Post #10





Grupa: Zarejestrowani
Postów: 20
Pomógł: 5
Dołączył: 13.04.2018

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


@Pyton_000, oczywiście że to rozwiązanie najgorsze. Uszeregowałem rozwiązania jakie przychodzą mi do głowy od najlepszego (Twojego). Zainteresowany sam wybierze, co mu odpowiada. Osobiście rekordowo indeksowałem 76 godzin :-)
Go to the top of the page
+Quote Post
Pyton_000
post 19.04.2018, 18:28:08
Post #11





Grupa: Zarejestrowani
Postów: 7 378
Pomógł: 1304
Dołączył: 26.10.2005

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


Spoko ja nie napisałem że jest złe :)Tylko tak jak powiedziałeś ostateczne rozwiązanie z tego co zaproponowałeś smile.gif
Go to the top of the page
+Quote Post
mmmmmmm
post 20.04.2018, 07:12:11
Post #12





Grupa: Zarejestrowani
Postów: 1 386
Pomógł: 302
Dołączył: 18.04.2012

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


fakt. mea culpa
Go to the top of the page
+Quote Post
fbi
post 20.04.2018, 20:27:29
Post #13





Grupa: Zarejestrowani
Postów: 6
Pomógł: 0
Dołączył: 6.10.2009

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


Witam, ponownie - nadal walczę z tym zapytaniem , wiem ze temat bardziej już z PHP,
Poniższe zapytanie działa niepoprawnie , zamienia zmienne tylko na minusowe id (- ) , nie wiem czy dodatkowo trzeba dodać zmienne z minusami ?

  1. $zamien = " START TRANSACTION";
  2. $statement = $dbh->prepare($zamien);
  3. $statement->execute();
  4. $zamien = "UPDATE planowanie_export
  5. SET id_kierowcy=
  6. CASE
  7. WHEN id_kierowcy= :nowy_kierowca THEN -:stary_kierowca
  8. WHEN id_kierowcy= :stary_kierowca THEN -:nowy_kierowca
  9. END
  10. WHERE id_kierowcy IN (:nowy_kierowca,:stary_kierowca)";
  11. $statement = $dbh->prepare($zamien);
  12. $statement->execute(
  13. ':nowy_kierowca' => $_POST["nowy_kierowca"],
  14. ':stary_kierowca' => $_POST["stary_kierowca"]
  15. )
  16. );
  17. $zamien = "UPDATE planowanie_export
  18. SET id_kierowcy= - id_kierowcy
  19. WHERE id_kierowcy IN (-nowy_kierowca,-:stary_kierowca)";
  20. $statement = $dbh->prepare($zamien);
  21. $statement->execute(
  22. ':nowy_kierowca' => $_POST["nowy_kierowca"],
  23. ':stary_kierowca' => $_POST["stary_kierowca"]
  24. )
  25. );
  26. $zamien = "COMMIT";
  27. $statement = $dbh->prepare($zamien);
  28. $statement->execute();



Przepraszam w Lini 20 pominąłem ":" - Po uzupełnieniu działa smile.gif

Ten post edytował fbi 20.04.2018, 20:39:01
Go to the top of the page
+Quote Post
trueblue
post 20.04.2018, 21:09:25
Post #14





Grupa: Zarejestrowani
Postów: 5 055
Pomógł: 1410
Dołączył: 11.03.2014

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


Zapytania możesz uprościć do:

  1. UPDATE kursy
  2. SET id_kierowcy = -id_kierowcy
  3. WHERE id_kierowcy IN (2,3);
  4.  
  5. UPDATE kursy
  6. SET id_kierowcy = 5 + id_kierowcy
  7. WHERE id_kierowcy IN (-2,-3);
Go to the top of the page
+Quote Post
Pyton_000
post 21.04.2018, 11:52:06
Post #15





Grupa: Zarejestrowani
Postów: 7 378
Pomógł: 1304
Dołączył: 26.10.2005

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


Zamiast "-:stary_kierowca" daj po prostu ":stary_kierowca" a jako wartość przekazuj wartość ujemną.
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: 22.06.2018 - 13:48