Probleme mit einem MYSQL Statement

  • C#

Es gibt 9 Antworten in diesem Thema. Der letzte Beitrag () ist von ErfinderDesRades.

    Probleme mit einem MYSQL Statement

    Guten Abend ich habe eine Frage zu einem von meinem SQL Statement. Iwie verstehe ich nicht genau was passiert.

    SQL-Abfrage

    1. MYSQL
    2. UPDATE users INNER JOIN tipps ON tipps.userID = users.userID SET users.points = CASE WHEN tipps.time < 1616697371 AND tipps.playernumber = 22 AND tipps.mannschaft = 'eck' THEN users.points+3

    Wenn ich den so ausführe sagt er mir 0 Datensätze betroffen und bekomme ich dann eine Warnung #1048 Feld points darf nicht null sein

    Sobald ich aber die Zahl dann größer als tipps.time ist führt er das Statement aus und setzt auch die users.points um 3 höher.
    Führe ich das Statement dann aber wieder aus und tipp.time wieder kleiner ist setzt er die user.points komischerweise auf 1

    Kann mir jemand erklären, was genau da passiert oder wo mein Fehler ist?

    Mit freundlichen Grüßen,
    Zaickz
    Du hast keinen ELSE-Fall.
    Wenn deine Bedingungen erfüllt sind hast du SET users.points = users.points+3
    Wenn sie nicht erfüllt sind: SET users.points = NULL und diese Spalte scheint nicht NULLABLE zu sein.

    SQL-Abfrage

    1. ​UPDATE users INNER JOIN tipps ON tipps.userID = users.userID SET users.points = CASE WHEN tipps.time < 1616697371 AND tipps.playernumber = 22 AND tipps.mannschaft = 'eck' THEN users.points+3 ELSE users.point
    --
    If Not Program.isWorking Then Code.Debug Else Code.DoNotTouch
    --
    Erstmal vielen Dank für deine Hilfe.

    Leider habe ich ein neues Problem.
    Das untere Set, also tipps.points, funktioniert einwandfrei. Das obere Set,also users.points, funktioniert leider nicht. Ich verstehe es absolut nicht warum nicht. Beide haben die gleiche Einstellung.Beide haben int(11)


    SQL-Abfrage

    1. UPDATE users INNER JOIN tipps ON tipps.userID = users.userID
    2. SET users.points = CASE
    3. WHEN tipps.playernumber = 15 AND tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618157551 THEN users.points+3
    4. WHEN tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618157551 THEN users.points+1
    5. ELSE users.points
    6. END,
    7. tipps.points = CASE
    8. WHEN tipps.playernumber = 15 AND tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618157551 THEN tipps.points+3
    9. WHEN tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618157551 THEN tipps.points+1
    10. ELSE tipps.points
    11. END
    12. ;SELECT * FROM tipps WHERE tipps.active = 1;UPDATE tipps SET active = 0
    Funktioniert doch.

    Im Ernst: Um sagen zu können "funktioniert nicht" musst du erstmal angeben, was denn passieren soll.
    Und dann, was stattdessen passiert.

    (Generell sieht mir das ganz abwegig aus, ein Update mit einem Inner Join zu kombinieren, und Setzungen in der übergeordneten Tabelle vorzunehmen.)
    Naja funktioniert nicht so ganz. Es ist gut möglich das Inner Join an dieser Stelle falsch gewählt ist, das will ich gar nicht bezweifeln. Leider kenne ich mich noch nicht so gut aus um etwas anderes zu behaupten.

    Was soll passieren?:
    Wenn tipps.playernumber = 15 ist und tipps.mannschaft = 'g' ist und tipp.active =1, dann sollen die users.points um 3 erhöht werden
    Wenn tipps.mannschaft='g' und tipp.active=1 ist, dann sollen die users.points um 1 erhöht werden.
    Gleiche Spiele in der anderen Tabelle nur mit tipps.points. Die time habe ich jetzt mal außenvor gelassen.

    Was passiert?:
    Die tipps.points werden um die jeweils festgelegte anzahl erhöht wenn die Bedingungen erfüllt sind

    Was passiert nicht?:
    Die users.points werde nicht erhöht obwohl es ja die gleich Bedigung ist.


    Das kuriose ist dieses Query macht beide Updates, ändere ich aber die Zahl auf z.B. playernumber=25 und ein tipp mit 25 - g und der passenden Zeit ist vorhanden sowie unten in der Tabelle zusehen, updated sich nur noch tipps.points

    Mit playernumber 70 hat er 2 betroffene Datensätze also einmal user.points und einmal tipps.points
    Mit plpayernumber 25 hat er nur noch 1 betroffenen Datensatz und zwar nur tipps.points

    SQL-Abfrage

    1. UPDATE users LEFT JOIN tipps ON tipps.userID = users.userID
    2. SET users.points = CASE
    3. WHEN tipps.playernumber = 70 AND tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618154782 THEN users.points+3
    4. WHEN tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618154782 THEN users.points+1
    5. ELSE users.points
    6. END,
    7. tipps.points = CASE
    8. WHEN tipps.playernumber = 70 AND tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618154782 THEN tipps.points+3
    9. WHEN tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618154782 THEN tipps.points+1
    10. ELSE tipps.points
    11. END
    12. ;SELECT * FROM tipps WHERE tipps.active = 1;UPDATE tipps SET active = 0



    Hier noch der Inhalt meiner tipps Tabelle

    SQL-Abfrage

    1. INSERT INTO `tipps` (`ID`, `userID`, `mannschaft`, `playernumber`, `time`, `changed`, `points`, `active`) VALUES
    2. (39, 152714596585570304, 'g', 70, 1618154761, 0, 0, 1),
    3. (40, 152714596585570304, 'g', 1, 1618225999, 0, 0, 0),
    4. (41, 152714596585570304, 'g', 25, 1618226477, 0, 0, 0);


    Ich habe jetzt nochmal ein wenig rumprobiert:

    SQL-Abfrage

    1. UPDATE users,tipps SET tipps.points = tipps.points+3, users.points = users.points+3 WHERE tipps.userID = users.userID
    Setz beide um points um 3 hoch

    SQL-Abfrage

    1. UPDATE users,tipps SET tipps.points = CASE WHEN tipps.userID = users.userID AND tipps.active = 1 THEN tipps.points+3 ELSE tipps.points END, users.points = CASE WHEN tipps.userID = users.userID AND tipps.active = 1 THEN users.points+3 ELSE users.points END
    Dies Query setzt nurnoch die users.points um 3 hoch aber nicht mehr die tipps.points.

    Ich bin ehrlich ich weiß wo genau mein Fehler liegt. Meiner Meinung nach sind doch bei beiden SET die Bedingungen doch immer erfüllt, das sie ja genau gleich sind!

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von „Zaickz“ ()

    Zaickz schrieb:

    Ich bin ehrlich ich weiß wo genau mein Fehler liegt.
    Nanu? Dann könntest du ihn doch beheben, und bräuchtest das Forum nicht.

    Zaickz schrieb:

    Meiner Meinung nach sind doch bei beiden SET die Bedingungen doch immer erfüllt, das sie ja genau gleich sind!
    Der Unterschied ist, dass der Update für die Tipps eines Users auf sich 3 vershiedene Tipp-Datensätze auswirkt.
    Der Update für den User hingegen wirkt sich dreimal auf denselben User-Datensatz aus.
    Was natürlich Quatsch ist, weil die verschiedenen Auswirkungen sich gegenseitig überschreiben, und übrig bleiben wird nur die letzte.
    Okay vielen Dank das bringt jetzt schonmal etwas Licht ins dunkle. Könnte ich das denn beheben wenn ich ein LIMIT setze oder bin ich damit auch noch auf dem falschen Weg? Hast du noch ein Tipp für mich. Ich möchte nicht die Lösung haben.

    EDIT:
    Ich glaube eine Lösung gefunden zu haben. Wäre nett wenn du mir diese mal verifizieren könntest oder ob es noch eine "schönere" Lösung für dieses Problem gibt.

    SQL-Abfrage

    1. UPDATE users INNER JOIN tipps ON tipps.userID = users.userID AND tipps.active = 1
    2. SET users.points = CASE
    3. WHEN tipps.playernumber = 1 AND tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618226000 THEN users.points+3
    4. WHEN tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618226000 THEN users.points+1
    5. ELSE users.points
    6. END,
    7. tipps.points = CASE
    8. WHEN tipps.playernumber = 1 AND tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618226000 THEN tipps.points+3
    9. WHEN tipps.mannschaft = 'g' AND tipps.active = 1 AND tipps.time < 1618226000 THEN tipps.points+1
    10. ELSE tipps.points
    11. END
    12. ;SELECT * FROM tipps WHERE tipps.active = 1;UPDATE tipps SET active = 0

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von „Zaickz“ ()

    Zaickz schrieb:

    eine "schönere" Lösung für dieses Problem
    Ich find SQL ist eine grauenhafte Sprache.
    Schöne Lösungen gibts da garnet.

    Mein Umgang mit Datenbanken geht vorzugsweise so, dass ich Daten in typisierter Form nach VB.Net hole, in VB.Net verarbeite, und wieder zurückschicke an die DB.
    Dazu verwende ich DataAdapter, die mir das Sql-Gehampel abnehmen.
    Also eine "schöne" Lösung ist, wenn ich gar kein Sql zu Gesicht bekomme.

    Na, ich übertreibe.
    Eine Tabelle abfragen ist ok - meinetwegen auch mit einem InnerJoin - aber das auch nur unter Beachtung bestimmter Einschränkungen.
    Updates formuliere ich nicht - das müssen meine DataAdapter machen.
    Und bei Set ... Case - Konstruktionen - da bin ich komplett draussen.

    (Ich übertreibe schonwieder.
    Weil auf Arbeit habich leider doch mehr als genug mit derlei Gekrampfe zu tun.)

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „ErfinderDesRades“ ()

    Falls dich dieser Ansatz interessiert:

    ErfinderDesRades schrieb:

    Mein Umgang mit Datenbanken geht vorzugsweise so, dass ich Daten in typisierter Form nach VB.Net hole, in VB.Net verarbeite, und wieder zurückschicke an die DB.
    Dazu verwende ich DataAdapter, die mir das Sql-Gehampel abnehmen.
    Also eine "schöne" Lösung ist, wenn ich gar kein Sql zu Gesicht bekomme.
    Sag bescheid - dann kann ich dich mit einschlägigen Tutorials totwerfen.