mysql: Case/When Abfrage liefert unerwartetes Ergebnis
Pit
- mysql
Hallo,
eine Tabelle:
mysql> select * FROM phppos_items_taxes;
+---------+-----------+---------+------------+
| item_id | name | percent | cumulative |
+---------+-----------+---------+------------+
| 1 | Tax 1 | 8.00 | 0 |
| 1 | Tax 2 | 10.00 | 1 |
| 3 | Sales Tax | 8.00 | 0 |
| 4 | Tax 1 | 20.00 | 0 |
| 4 | Tax 2 | 20.00 | 0 |
+---------+-----------+---------+------------+
liefert zur Query:
SELECT
SUM(
CASE
WHEN cumulative = 1 THEN percent
WHEN cumulative = '' THEN 1000
ELSE 0
END)
FROM phppos_items_taxes;
das Ergebnis:
4010
Ich hatte 10
erwartet.
Kann mir jemand erklären, warum mysql das hier macht?
Zusatz: Die Spalte "cumulative" ist vom Typ int
.
Gruß, Pit
Tach!
Kann mir jemand erklären, warum mysql das hier macht? Zusatz: Die Spalte "cumulative" ist vom Typ
int
.
Die eigentliche Frage ist, warum du diese Spalte dann mit einem Leerstring zu vergleichen versuchst. MySQL versucht jedenfalls die beiden unterschiedlichen Typen zu vergleichen und konvertiert den Leerstring in eine Zahl: 0.
dedlfix.
Hallo dedlfix,
Die eigentliche Frage ist, warum du diese Spalte dann mit einem Leerstring zu vergleichen versuchst.
Deine erste Frage ist natürlich berechtigt. Mich interessiert es einfach, deshalb frage ich nach. Natürlich versuche ich das in der Praxis zu vermeiden.
MySQL versucht jedenfalls die beiden unterschiedlichen Typen zu vergleichen und konvertiert den Leerstring in eine Zahl: 0.
Müßte aber nicht dann eine Abfrage ala:
SELECT
SUM(
CASE
WHEN cumulative = 1 THEN percent
WHEN cumulative = 'auzzuuisdfhiwq' THEN 1000
ELSE 0
END)
FROM phppos_items_taxes;
10
ergeben?
Das Ergebnis ist aber wieder 4010
.
Gruß, Pit
Tach!
Müßte aber nicht dann eine Abfrage ala:
SELECT SUM( CASE WHEN cumulative = 1 THEN percent WHEN cumulative = 'auzzuuisdfhiwq' THEN 1000 ELSE 0 END) FROM phppos_items_taxes;
10
ergeben?
Die eigentliche Frage ist, wie unterschiedliche Typen miteinander verglichen werden, beziehungsweise wie Strings in Zahlen konvertiert werden. Dein String ist jedenfalls keine Zahl und bei der Konvertierung kommt 0 raus.
dedlfix.
Das ist zu erwarten.
> select "uzzuuisdfhiwq" = 0;
+---------------------+
| "uzzuuisdfhiwq" = 0 |
+---------------------+
| 1 |
+---------------------+
1 row in set, 1 warning (0.00 sec)
> select 0 = "uzzuuisdfhiwq";
+---------------------+
| 0 = "uzzuuisdfhiwq" |
+---------------------+
| 1 |
+---------------------+
1 row in set, 1 warning (0.00 sec)
> select "uzzuuisdfhiwq" = CONVERT(0 using ASCII) ;
+------------------------------------------+
| "uzzuuisdfhiwq" = CONVERT(0 using ASCII) |
+------------------------------------------+
| 0 |
+------------------------------------------+
1 row in set (0.00 sec)
> select "" = CONVERT(0 using ASCII);
+-----------------------------+
| "" = CONVERT(0 using ASCII) |
+-----------------------------+
| 0 |
+-----------------------------+
1 row in set (0.00 sec)
Hallo dedlfix, Hallo Ursus,
ok, ich verstehe es.
Jeglicher String wird also von mysql als 0 interpretiert, korrekt?
Sowas in dieser Art hatte bei mir nämlich zu einem Fehler geführt, den ich mir nicht erklären konnte. Die Abfrage und der Vergleich eines String mit einer Integer-Spalte rührte daher, dass ich die Abfrage aus einer anderen Abfrage übernommen hatte. Die entsprechende Tabelle hatte aber eine varchar-Spalte…
Danke für Eure Hilfe,
Pit
Jeglicher String wird also von mysql als 0 interpretiert, korrekt?
Nein.
> select 1 = "1abc";
+------------+
| 1 = "1abc" |
+------------+
| 1 |
+------------+
1 row in set, 1 warning (0.00 sec)
> select 1 = "abc1";
+------------+
| 1 = "abc1" |
+------------+
| 0 |
+------------+
1 row in set, 1 warning (0.00 sec)
Jeglicher String, der sich nicht als Zahl interpretieren lässt (konkret mit der Darstellung einer solchen beginnt) wird beim Vergleich mit einer Zahl zu 0 konvertiert.
Kann mir jemand erklären, warum mysql das hier macht?
Ich.
> select "" = 0;
+--------+
| "" = 0 |
+--------+
| 1 |
+--------+
1 row in set, 1 warning (0.00 sec)
> select 0 = "";
+--------+
| 0 = "" |
+--------+
| 1 |
+--------+
1 row in set, 1 warning (0.00 sec)