Postgres mise à jour à partir d'une jointure gauche
Je suis nouveau dans PostgreSQL et tenter de convertir une requête à partir de SQL Server.
J'ai une table Utilisateurs, avec, entre autres, les colonnes bUsrActive, bUsrAdmin et sUsrClientCode. Je veux mettre à jour des Utilisateurs et définir bUsrActive = false si il n'existe pas qu'un autre utilisateur avec le même sUsrClientCode où bUsrAdmin = true et bUsrActive = true.
Dans SQL Server j'ai cette requête
UPDATE u SET u.bUsrActive = 0
FROM Users u
LEFT JOIN Users u2 ON u.sUsrClientCode = u2.sUsrClientCode AND u2.bUsrAdmin = 1 AND u2.bUsrActive = 1
WHERE u.bUsrAdmin = 0 AND u.bUsrActive = 1 AND u2.nkUsr IS NULL
Je suis en train de convertir cette postgres. J'ai écrit 3 approches.
1) Ma première tentative. Évidemment pas de travail.
UPDATE Users u
SET bUsrActive = false
FROM Users u2
WHERE u.sUsrClientCode = u2.sUsrClientCode AND u2.bUsrAdmin = true AND u2.bUsrActive = true
AND u.bUsrAdmin = false AND u.bUsrActive = true AND u2.nkUsr IS NULL;
2) je comprends pas pourquoi ça ne fonctionne pas (il les mises à jour de tous les utilisateurs). Je ne peux pas comprendre comment le tableau de référence des Utilisateurs de u dans la mise à JOUR ... JEU de la partie.
UPDATE Users
SET bUsrActive = false
FROM Users u
LEFT JOIN Users u2 ON u.sUsrClientCode = u2.sUsrClientCode AND u2.bUsrAdmin = true AND u2.bUsrActive = true
WHERE u.bUsrAdmin = false AND u.bUsrActive = true AND u2.nkUsr IS NULL;
3) Le paragraphe suivant est le travail, mais pas à l'aide de la rejoindre.
UPDATE Users
SET bUsrActive = false
WHERE NOT EXISTS (
SELECT 1
FROM Users u
WHERE u.sUsrClientCode = Users.sUsrClientCode AND u.bUsrAdmin = true AND u.bUsrActive = true
) AND Users.bUsrAdmin = false AND Users.bUsrActive = true;
Je vais probablement aller avec la dernière solution. Je voulais juste savoir si il est possible de faire ce que je veux à l'aide d'une jointure gauche.
Rien, c'est le travail. Je me demandais si je peux le faire dans l'autre sens: à l'aide de jointures. Semble plus agréable à l'oeil! Je suppose que le rendement sera le même.
Le second doit travailler (à première vue) quelle est l'erreur que vous obtenez?. Savez-vous que la sémantique de la
FROM
clause est différent dans PostgreSQL par rapport à SQL Server?Je suis nouveau et de l'apprentissage aujourd'hui. Le deuxième sera mis à jour tous les enregistrements dans la table des Utilisateurs, et pas seulement les "Utilisateurs u".
OriginalL'auteur alfoks | 2013-01-24
Vous devez vous connecter pour publier un commentaire.
Voici une méthode générique permettant de transformer cette requête de mise à jour de SQL-server forme de PostgreSQL:
ctid est un pseudo-colonne qui pointe vers l'emplacement unique de un ligne. Vous pouvez utiliser à la place de la clé primaire de la table si il en avait un.
La requête n ° 2 de la question n'est pas de faire ce que vous souhaitez parce que la mise à jour de la table
Users
n'est jamais joint à la même tableUsers u
dans la clause from. Tout comme lorsque vous mettez un nom de table deux fois dans une clause from, ils ne reçoivent pas implicitement jointes ou liées ensemble, ils sont considérés comme deux indépendants des ensembles de lignes.OriginalL'auteur Daniel Vérité
Je pense que c'est la bonne façon de faire les 2) je pense qu'il est plus optimal/efficace que de faire une sous-sélection.
vous pouvez l'alias de la table de mise à jour. Vous ne pouvez pas utiliser cet alias dans la clause SET.
Ce n'est pas syntaxiquement correct.
testé contre 9,5 et il fonctionne comme prévu, il a beaucoup plus de sens et est plus rapide qu'une sous-requête. jusqu'.
OriginalL'auteur Clive Paterson