Maison > base de données > tutoriel mysql > le corps du texte

Comment échanger les valeurs de ligne dans MySQL avec une contrainte unique sans violer l'intégrité ?

Linda Hamilton
Libérer: 2024-10-26 00:23:28
original
151 Les gens l'ont consulté

How to Swap Row Values in MySQL with a Unique Constraint Without Violating Integrity?

Échanger les valeurs de ligne dans MySQL tout en préservant la contrainte unique

Dans MySQL, la tâche d'échanger les valeurs de priorité entre deux lignes dans une table avec un une contrainte unique peut rencontrer des erreurs dues à des violations de contrainte. Pour comprendre le problème, examinons une instruction UPDATE typique :

UPDATE tasks 
SET priority = 
CASE
    WHEN priority=2 THEN 3 
    WHEN priority=3 THEN 2 
END 

WHERE priority IN (2,3);
Copier après la connexion

Cette instruction entraîne cependant une erreur :

Error Code: 1062. Duplicate entry '3' for key 'priority_UNIQUE'
Copier après la connexion

Nature du problème

MySQL traite les mises à jour différemment des autres SGBD. Il vérifie les violations de contraintes après chaque mise à jour de ligne, plutôt qu'une fois l'instruction entière terminée. Par conséquent, l'échange de valeurs viole directement la contrainte unique.

Alternatives sans valeurs fausses ni requêtes multiples

Malheureusement, il n'existe aucun moyen d'effectuer cette opération sans utiliser un valeur intermédiaire (fausse ou nulle) ou requêtes multiples dans MySQL. La contrainte unique impose l'unicité après chaque mise à jour de ligne, rendant l'échange direct impossible.

Suppression temporaire de la contrainte

Une option consiste à supprimer temporairement la contrainte unique, à exécuter l'opération d'échange , puis rajoutez la contrainte. Cependant, cette approche n'est pas recommandée car elle compromet l'intégrité des données.

Fausses valeurs et requêtes multiples

L'approche recommandée consiste à utiliser une fausse valeur (-3) pour temporairement maintenez la valeur de priorité de la première ligne et échangez-la avec la valeur de la deuxième ligne. Deux requêtes au sein d'une transaction sont requises :

START TRANSACTION ;
    UPDATE tasks 
    SET priority = 
      CASE
        WHEN priority = 2 THEN -3 
        WHEN priority = 3 THEN -2 
      END 
    WHERE priority IN (2,3) ;

    UPDATE tasks 
    SET priority = - priority
    WHERE priority IN (-2,-3) ;
COMMIT ;
Copier après la connexion

Ce processus garantit que la contrainte n'est pas violée lors de l'opération d'échange.

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

source:php.cn
Déclaration de ce site Web
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn
Derniers articles par auteur
Tutoriels populaires
Plus>
Derniers téléchargements
Plus>
effets Web
Code source du site Web
Matériel du site Web
Modèle frontal
À propos de nous Clause de non-responsabilité Sitemap
Site Web PHP chinois:Formation PHP en ligne sur le bien-être public,Aidez les apprenants PHP à grandir rapidement!