Risposte:
La pagina di documentazione MSDN su ALTER TABLEspiega questi:
ALTER TABLE: modifica la struttura della tabella CHECK CONSTRAINT ..: abilita il vincoloNOCHECK CONSTRAINT ..: disabilita il vincolo WITH CHECK: controlla anche il vincoloWITH NOCHECK: non verifica il vincoloNelle loro parole:
| [ WITH { CHECK | NOCHECK } ] { CHECK | NOCHECK } CONSTRAINT { ALL | constraint_name [ ,...n ] }...
WITH CHECK | WITH NOCHECKSpecifica se i dati nella tabella sono o meno convalidati rispetto a un nuovo aggiunto, riattivatoFOREIGN KEYoCHECKvincolo . Se non specificato,WITH CHECKviene assunto per nuovi vincoli eWITH NOCHECKassunto per vincoli riattivati.Se non si desidera verificare nuovi
CHECKoFOREIGN KEYvincoli rispetto ai dati esistenti, utilizzareWITH NOCHECK. Non è consigliabile farlo, tranne in rari casi. Il nuovo vincolo verrà valutato in tutti gli aggiornamenti successivi dei dati. Qualsiasi violazione del vincolo che viene soppressaWITH NOCHECKquando viene aggiunto il vincolo può causare errori futuri in caso di aggiornamento di righe con dati non conformi al vincolo.Query Optimizer non considera i vincoli definiti
WITH NOCHECK. Tali vincoli vengono ignorati fino a quando non vengono riattivati utilizzando laALTER TABLEtabellaWITH CHECK CHECK CONSTRAINT ALL....
{ CHECK | NOCHECK } CONSTRAINT
Specifica che Vincolo_nome è abilitato o disabilitato. Questa opzione può essere utilizzata solo conFOREIGN KEYeCHECKvincoli. QuandoNOCHECKviene specificato, il vincolo è disabilitato e i futuri inserimenti o aggiornamenti alla colonna non vengono convalidati rispetto alle condizioni del vincolo.DEFAULT,PRIMARY KEYe iUNIQUEvincoli non possono essere disabilitati.
Test in dbfiddle :
CREATE TABLE a (aid INT PRIMARY KEY);PARTIRE
✓
INSERT INTO a (aid) VALUES (1), (2), (3) ;PARTIRE
3 file interessate
CREATE TABLE b ( aid INT, bid INT PRIMARY KEY, CONSTRAINT [My_FORIEGN_KEY] FOREIGN KEY (aid) REFERENCES a (aid) ) ;PARTIRE
✓
INSERT INTO b (aid, bid) VALUES (1, 11), (1, 12), (2, 21), (3, 31) ;PARTIRE
4 file interessate
INSERT INTO b (aid, bid) VALUES (6, 61), (6, 62) ;PARTIRE
Messaggio 547 livello 16 stato 0 riga 1 L'istruzione INSERT è in conflitto con il vincolo FOREIGN KEY "My_FORIEGN_KEY". Il conflitto si è verificato nel database "fiddle_792fce5de09f42908c3a0f91421f3522", tabella "dbo.a", colonna "help". Messaggio 3621 Livello 0 Stato 0 Riga 1 La dichiarazione è stata chiusa.
SELECT * FROM b ;PARTIRE
aiuto | offerta -: | -: 1 | 11 1 | 12 2 | 21 3 | 31
ALTER TABLE b NOCHECK CONSTRAINT [My_FORIEGN_KEY]; --disablePARTIRE
✓
INSERT INTO b (aid, bid) VALUES (4, 41), (4, 42) ;PARTIRE
2 file interessate
SELECT * FROM b ;PARTIRE
aiuto | offerta -: | -: 1 | 11 1 | 12 2 | 21 3 | 31 4 | 41 4 | 42
ALTER TABLE b WITH NOCHECK CHECK CONSTRAINT [My_FORIEGN_KEY]; -- enable constraint without checking existing dataPARTIRE
✓
SELECT * FROM b ;PARTIRE
aiuto | offerta -: | -: 1 | 11 1 | 12 2 | 21 3 | 31 4 | 41 4 | 42
INSERT INTO b (aid, bid) VALUES (6, 61), (6, 62) ;PARTIRE
Messaggio 547 livello 16 stato 0 riga 1 L'istruzione INSERT è in conflitto con il vincolo FOREIGN KEY "My_FORIEGN_KEY". Il conflitto si è verificato nel database "fiddle_792fce5de09f42908c3a0f91421f3522", tabella "dbo.a", colonna "help". Messaggio 3621 Livello 0 Stato 0 Riga 1 La dichiarazione è stata chiusa.
SELECT * FROM b ;PARTIRE
aiuto | offerta -: | -: 1 | 11 1 | 12 2 | 21 3 | 31 4 | 41 4 | 42
ALTER TABLE b WITH CHECK CHECK CONSTRAINT [My_FORIEGN_KEY]; -- check existing data and enable constraintPARTIRE
Messaggio 547 livello 16 stato 0 riga 1 L'istruzione ALTER TABLE è in conflitto con il vincolo FOREIGN KEY "My_FORIEGN_KEY". Il conflitto si è verificato nel database "fiddle_792fce5de09f42908c3a0f91421f3522", tabella "dbo.a", colonna "help".
Valuta di leggere l'articolo qui: https://msdn.microsoft.com/en-us/library/ms190273.aspx
Ci dice: 'Query Optimizer non considera i vincoli definiti CON NOCHECK. Tali vincoli vengono ignorati fino a quando non vengono riattivati utilizzando la tabella ALTER TABLE CON CHECK CHECK CONSTRAINT ALL '
Inoltre, considera questo thread su StackOverflow: /programming/529941/with-check-add-constraint-followed-by-check-constraint-vs-add-constraint
ALTER TABLE b WITH NOCHECK CHECK CONSTRAINT [My_FORIEGN_KEY]; -- enable constraint without checking, questo significa che il vincolo non controllerà i dati esistenti, ma solo i nuovi dati in arrivo?