Ich habe zwei Tische: einen user
Tisch und einen friendship
Tisch. Angenommen, die friendship
Tabelle sieht folgendermaßen aus:
friendship
------------
user_one_id
user_two_id
other_fields
Ich brauche die Durchsetzung Einzigartigkeit der Kombination von Werten (user_one_id, user_two_id)
und ignorieren Sie die Bestellung , so:
user_one_id | user_two_id
------------+------------
1 | 2
2 | 1 -- the DBMS should throw a unique constraint error when trying to insert a row like this one.
Ein weiterer wichtiger Punkt ist, dass user_one_id
er den Initiator von friendship
und user_two_id
den Empfänger darstellt , sodass ich nicht einfach die "kleinere" der beiden IDs machen kann user_one_id
.
Die Frage
Gibt es eine Möglichkeit, dies mithilfe von Einschränkungen zu tun, oder sollte ich dies auf eine andere Weise implementieren?
ERROR: index "friendship_greatest_least_idx" contains expressions LINE 1: alter table friendship add primary key using index friendshi... ^ DETAIL: Cannot create a primary key or unique constraint using such an index
Die Lösung ist sehr gut. Zunächst sollten wir jedoch sicherstellen, dass die beiden Spalten keine Überlappungszahlen enthalten. Das heißt, eine Zahl ist für eine Spalte eindeutig.
Ich würde die folgende einfache Lösung vorschlagen:
Erstellen Sie zwei Sequenzen:
1.
user_one_id_seq: mit geraden Zahlen
user_two_id_seq mit ungeraden Zahlen
2.
user_one_id_seq: Zahlen zwischen 1 und 10000
user_two_id_seq Zahlen zwischen 10001 und 20000
quelle
Das Design sollte normalisiert werden, indem eine Schnittpunkttabelle mit dem Namen user_friendship erstellt wird:
Tabelle erstellen user_friendship (Benutzer-ID int NICHT NULL, Freundschafts-ID int NICHT NULL, PRIMARY KEY (Benutzer-ID, Freundschafts-ID), AUSLÄNDISCHER SCHLÜSSEL Freundschafts-ID REFERENZEN Freundschaft (Freundschafts-ID), AUSLÄNDISCHER SCHLÜSSEL Benutzer-ID REFERENZEN Benutzer (Benutzer-ID)
);
quelle
Wenn Sie die Logik so einstellen, dass der Wert von user_one_id niedriger als der Wert von user_two_id ist , treten keine Probleme auf .
quelle
user_one_id
Repräsentiert für meinen Anwendungsfall den Initiator der Freundschaft unduser_two_id
den Empfänger der Freundschaft. Ich kann also nicht einfach den niedrigsten Wert als verwendenuser_one_id
.