Aggiungi una colonna calcolata persistente che combina le 18 chiavi, quindi crea un indice univoco sulla colonna calcolata:
alter table t add all_keys as c1+c2+c3+...+c18 persisted;
create unique index i18 on t (all_keys);
Consulta la sezione Creazione di indici su colonne calcolate .
Un altro approccio è quello di creare una vista indicizzata:
create view v
with schemabinding
as select c1+c2+c3+...+c18 as all_keys
from dbo.t;
create unique clustered index c18 on v(all_keys);
Vedi Creazione di viste indicizzate .
Entrambi gli approcci consentono un aggregato chiave parziale: aggregato c1 + c2 + c3 come k1, c4 + c5 + c6 come k2 ecc. Quindi indicizza / crea una vista indicizzata su (k1, k2, ...). Questo potrebbe essere utile per le scansioni dell'intervallo (l'indice può essere utilizzato per la ricerca su c1 + c2 + c3.
Naturalmente, tutte le +
operazioni nel mio esempio sono aggregazioni di stringhe, l'operatore effettivo da utilizzare dipende dai tipi di tutte quelle colonne (ad esempio, potrebbe essere necessario utilizzare cast espliciti).
PS. Poiché i vincoli univoci vengono applicati da un indice univoco, qualsiasi restrizione sugli indici univoci si applicherà anche ai vincoli univoci:
create table t (
c1 char(3), c2 char(3), c3 char(3), c4 char(3),
c5 char(3), c6 char(3), c7 char(3), c8 char(3),
c9 char(3), c10 char(3), c11 char(3), c12 char(3),
c13 char(3), c14 char(3), c15 char(3), c16 char(3),
c17 char(3), c18 char(3), c19 char(3), c20 char(3),
constraint unq unique
(c1,c2,c3,c4,c5,c6,c7,c8,c9,c10,c11,c12,c13,c14,c15,c16,c17,c18));
go
Msg 1904, Level 16, State 1, Line 3
The index '' on table 't' has 18 column names in index key list.
The maximum limit for index or statistics key column list is 16.
Msg 1750, Level 16, State 0, Line 3
Could not create constraint. See previous errors.
Tuttavia, la creazione del vincolo su una colonna calcolata persistente funziona:
create table t (
c1 char(3), c2 char(3), c3 char(3), c4 char(3),
c5 char(3), c6 char(3), c7 char(3), c8 char(3),
c9 char(3), c10 char(3), c11 char(3), c12 char(3),
c13 char(3), c14 char(3), c15 char(3), c16 char(3),
c17 char(3), c18 char(3), c19 char(3), c20 char(3),
all_c as
c1+c2+c3+c4+c5+c6+c7+c8+c9+c10+c11+
c12+c13+c14+c15+c16+c17+c18
persisted
constraint unq unique (all_c));
go
Ovviamente, la colonna persistente consuma lo spazio sul disco, quindi l'approccio potrebbe essere negativo per una tabella molto grande. L'approccio con vista indicizzata non presenta questo problema, consuma solo lo spazio per l' indice , non lo spazio per la colonna e l' indice calcolati .