SQL-Abfrage mit zwei Spalten und unterschiedlichen Werten in einer Spalte

Caro*17

Newbie
Registriert
Apr. 2020
Beiträge
3
Hallo,
ich bin neu hier und habe eine Frage zu SQL.

Ich habe zwei Spalten, wobei in Spalte A ein Wert öfters vorkommen kann und in Spalte B mitunter unterschiedliche Werte stehen.

Spalte ASpalte B
1A
1B
1A
2C
2C
3D
3D
3E

Jetzt möchte ich innerhalb der gleichen Nummer von Spalte A (z. B. Nummer 1) die Spalte B prüfen (hier kommen nur die ersten drei Zeilen in Betracht, da nur die ersten drei Zeilen die gleiche Nummer haben), ob es hier unterschiedliche Werte gibt.

Das Ergebnis wäre:
Spalte A: Nummer 1, Spalte B: Buchstabe A und B
Spalte A: Nummer 2, Spalte B: Buchstabe C => würde nicht als Ergebnis erscheinen, da es hier keine differierenden Angaben gibt.
Spalte A: Nummer 3, Spalte B: Buchstabe D und E

Ich hoffe, ich konnte es eindeutig erklären, ansonsten einfach nachfragen. Danke!
 
Wenn ich es richtig verstanden habe..


SQL:
SELECT A, B, COUNT(B) AS count
FROM table
GROUP BY B
HAVING count > 1;


Edit: nee, das passt nicht... :D
 
  • Gefällt mir
Reaktionen: Bloodie24
Das sollte sich einfach mit DISTINCT erschlagen lassen:
Code:
SELECT DISTINCT spalteA, spalteB FROM table
 
@benneq so kommt aber auch "2, C" zurück, was es nicht soll, wenn ich es richtig verstanden habe.
 
  • Gefällt mir
Reaktionen: benneq
Jetzt aber:

edit: nochmal ein wenig verbessert

SQL:
SELECT DISTINCT A, B
FROM test
WHERE A IN (
    SELECT A
    FROM test
    GROUP BY A
    HAVING COUNT(DISTINCT B) > 1
);

1A
1B
3D
3E
 
Eventuell geht es auch ohne Subselect aber so geht es auf jeden Fall wie ich es verstanden habe. Vielleicht postest du nochmal das erwartete Ergebnis.
SQL:
create table calc(a int, b varchar(1));

insert into calc values(1, 'A');
insert into calc values(1, 'B');
insert into calc values(1, 'A');
insert into calc values(2, 'C');
insert into calc values(2, 'C');
insert into calc values(3, 'D');
insert into calc values(3, 'D');
insert into calc values(3, 'E');

select
    calc.a,
    calc.b
from
    calc,
    (select
        a
    from
        calc
    group by
        a
    having
        count(distinct b)>1) as foo
where calc.a = foo.a;

Ergebnis:
Code:
1|A
1|B
1|A
3|D
3|D
3|E
 
Eine mögliche Lösung:

SQL:
 select distinct c2.a, c2.b from calc c1 join calc c2 on c1.a=c2.a and c1.b <> c2.b;
Allerdings gefällt sie mir nicht so richtig, da die Ergebnismenge verdoppelt ist- (a; b) und (b; a) tauchen beide im Ergebnis auf, wenn man das DISTINCT wegläßt.

Für größere Datenmengen also eher nicht so das Wahre.
 
  • Gefällt mir
Reaktionen: Bagbag
Was wäre denn für größere Datenmengen so das Wahre?
Ergänzung ()

Ich habe diese Variante ausprobiert.

SELECT DISTINCT A, B
FROM test
WHERE A IN (
SELECT A
FROM test
GROUP BY A
HAVING COUNT(DISTINCT B) > 1
);

Und sie funktioniert. Vielen Dank an alle Beteiligten.

Beim zweiten Vorschlag bin ich mir nicht sicher, ob das überhaupt funktionieren würde, da ich die Werte nicht kenne und es um Daten im Millionenbereich geht.
 
Zuletzt bearbeitet:
Bei Daten im Millionenbereich ist die obige Abfrage nicht sehr gut. Unterabfragen in der Where-Bedingung sind generell zu vermeiden, stattdessen sollte da ein inner join kommen.
Sollten die Werte auch tatsächlich in eine Zeile kommen so wie oben beschrieben? Das macht die Sache nämlich schon etwas komplizierter.
 
Eh... Dir ist hoffentlich klar, daß die Einschränkung auch für diese Variante gilt? Alles wo man DISTINCT braucht ist erstmal fragwürdig.
Da der erste Vorschlag nicht korreliert ist, würde ich vorsichtig unterstellen, daß die Abfragen gleichwertig sind.
Natürlich kennt keiner die Daten. Abfragen, die Kenntnis der Daten voraussetzen, sind wertlos und können unbesehen in den Müll.

Weitergehend, wenn nicht schon auf dem Schirm: den Query Plan der Abfrage mal auf den Produktivdaten laufenlassen (oder Testdaten, solange diese ein ausreichend repräsentatives Abbild der Produktivdaten sind) und schauen, ob/wo Indices benötigt werden. Das ist relevanter als eine ober Schranke von n*2 Ergebnisdaten.


@Oelepoeto naja so ganz pauschal auch nicht, aber man muß halt aufpassen, daß nicht korreliert. Ohne Subqueries ist das einfacher. im Vorschlag oben wird die Subquery auch nur einmal ausgeführt (statt einmal pro Datensatz).

Aber man sollte möglichst ohne DISTINCT auskommen.
 
Zurück
Oben