SQLite
 sql >> Base de données >  >> RDS >> SQLite

Convertir les valeurs NULL en valeur par défaut de la colonne lors de l'insertion de données dans SQLite

L'une des extensions non standard de SQLite pour SQL est le ON CONFLICT clause.

Cette clause vous permet de déterminer ce qui doit se passer lorsque certains conflits surviennent en raison d'une violation de contrainte.

L'une des choses pour lesquelles vous pouvez utiliser cette clause est de remplacer NULL valeurs par la valeur par défaut d'une colonne lors de l'insertion ou de la mise à jour de données dans une table.

Par défaut, si vous essayez d'insérer explicitement NULL dans une colonne avec un NOT NULL contrainte, cela échouera.

Et si vous essayez d'insérer explicitement NULL dans une colonne sans un NOT NULL contrainte, puis NULL sera assigné à cette colonne, même s'il y a un DEFAULT clause.

Cependant, vous pouvez utiliser le ON CONFLICT clause pour la définir sur la valeur par défaut au lieu de NULL .

Exemple

Le code suivant illustre ce que je veux dire.

DROP TABLE IF EXISTS Products;

CREATE TABLE Products( 
    ProductId INTEGER PRIMARY KEY, 
    ProductName NOT NULL, 
    Price NOT NULL ON CONFLICT REPLACE DEFAULT 0.00
);

INSERT INTO Products (ProductId, ProductName, Price) VALUES 
    (1, 'Widget Holder', NULL);

SELECT * FROM Products;

Dans cet exemple, j'utilise ON CONFLICT REPLACE pour définir NULL valeurs à la valeur par défaut au lieu de NULL .

Voici le résultat du SELECT déclaration sur la dernière ligne :

ProductId   ProductName    Price     
----------  -------------  ----------
1           Widget Holder  0.0       

Nous pouvons voir que le Prix la colonne a la valeur par défaut de 0.0 même si j'ai essayé d'insérer explicitement NULL .

Voyons ce qui se passe si je supprime le NOT NULL contrainte.

DROP TABLE IF EXISTS Products;

CREATE TABLE Products( 
    ProductId INTEGER PRIMARY KEY, 
    ProductName NOT NULL, 
    Price DEFAULT 0.00
);

INSERT INTO Products (ProductId, ProductName, Price) VALUES 
    (1, 'Widget Holder', NULL);

SELECT * FROM Products;

Résultat :

ProductId   ProductName    Price     
----------  -------------  ----------
1           Widget Holder            

Maintenant, la colonne contient NULL .

Insérer NULL implicitement

Il est important de noter que cet article concerne principalement l'insertion de NULL explicitement .

Si vous essayez d'insérer NULL implicitement , l'exemple précédent produira un résultat différent.

Ce que je veux dire, c'est que si vous n'incluez pas la colonne dans le INSERT déclaration, le DEFAULT contrainte sera utilisée automatiquement. C'est ce que DEFAULT les contraintes sont pour - pour fournir une valeur lorsque vous n'en fournissez pas explicitement.

Voici ce qui se passe lorsque je fais cela.

DROP TABLE IF EXISTS Products;

CREATE TABLE Products( 
    ProductId INTEGER PRIMARY KEY, 
    ProductName NOT NULL, 
    Price DEFAULT 0.00
);

INSERT INTO Products (ProductId, ProductName) VALUES 
    (1, 'Widget Holder');

SELECT * FROM Products;

Résultat :

ProductId   ProductName    Price     
----------  -------------  ----------
1           Widget Holder  0.0       

Donc, tout ce que j'ai fait, c'est supprimer le Prix colonne de INSERT déclaration.

EN CONFLIT pour l'instruction INSERT

Le premier exemple utilise ON CONFLICT sur le CREATE TABLE déclaration.

Mais que se passe-t-il si la table n'a pas été créée avec le ON CONFLICT clause ?

Heureusement, il existe également un moyen de l'utiliser sur le INSERT déclaration.

La syntaxe est légèrement différente. Lorsqu'il est utilisé sur le INSERT déclaration que vous devez remplacer ON CONFLICT avec OR .

Modifions le code pour utiliser cette méthode.

DROP TABLE IF EXISTS Products;

CREATE TABLE Products( 
    ProductId INTEGER PRIMARY KEY, 
    ProductName NOT NULL, 
    Price NOT NULL DEFAULT 0.00
);

INSERT OR REPLACE INTO Products (ProductId, ProductName, Price) VALUES 
    (1, 'Widget Holder', NULL);

SELECT * FROM Products;

Résultat :

ProductId   ProductName    Price     
----------  -------------  ----------
1           Widget Holder  0.0       

J'ai donc remplacé INSERT INTO avec INSERT OR REPLACE INTO .

Voici quel serait le résultat si je n'avais pas inséré cette clause.

DROP TABLE IF EXISTS Products;

CREATE TABLE Products( 
    ProductId INTEGER PRIMARY KEY, 
    ProductName NOT NULL, 
    Price NOT NULL DEFAULT 0.00
);

INSERT INTO Products (ProductId, ProductName, Price) VALUES 
    (1, 'Widget Holder', NULL);

SELECT * FROM Products;

Résultat :

Error: NOT NULL constraint failed: Products.Price

Pas de contrainte DEFAULT ?

Dans le cas où vous utilisez le ON CONFLICT clause sur une colonne sans DEFAULT contrainte, l'instruction SQL est abandonnée avec une erreur SQLITE_CONSTRAINT toutes les modifications apportées par l'instruction SQL actuelle sont annulées ; mais les modifications causées par les instructions SQL précédentes dans la même transaction sont conservées et la transaction reste active.