Sqlserver
 sql >> Database >  >> RDS >> Sqlserver

5 modi per trovare righe che contengono lettere maiuscole in SQL Server

Di seguito sono elencate cinque opzioni per la restituzione di righe che contengono lettere maiuscole in SQL Server.

Dati di esempio

Supponiamo di avere una tabella con i seguenti dati:

SELECT c1 FROM t1;

Risultato:

+----------------+
| c1             |
|----------------|
| CAFÉ           |
| Café           |
| café           |
| 1café          |
| eCafé          |
| James Bond 007 |
| JB 007         |
| 007            |
| NULL           |
|                |
| É              |
| É 123          |
| é              |
| é 123          |
| ø              |
| Ø              |
+----------------+

Possiamo usare i seguenti metodi per restituire le righe che contengono lettere maiuscole.

Opzione 1:confronta con LOWER() Stringa

Possiamo usare il LOWER() funzione per confrontare il valore originale con il suo equivalente minuscolo:

SELECT c1 FROM t1
WHERE LOWER(c1) COLLATE Latin1_General_CS_AS <> c1;

Risultato:

+----------------+
| c1             |
|----------------|
| CAFÉ           |
| Café           |
| eCafé          |
| James Bond 007 |
| JB 007         |
| É              |
| É 123          |
| Ø              |
+----------------+

Utilizzando il diverso a (<> ) operatore (puoi in alternativa usare != invece di <> se preferisci), restituiamo solo quelle righe che sono diverse dai loro equivalenti minuscoli. Il motivo per cui lo facciamo è perché, se un valore è uguale al suo equivalente minuscolo, all'inizio era già minuscolo (e non vogliamo restituirlo).

Usiamo anche COLLATE Latin1_General_CS_AS per specificare in modo esplicito un confronto con distinzione tra maiuscole e minuscole (e con accento). Senza questo, potresti ottenere risultati imprevisti, a seconda delle regole di confronto utilizzate sul tuo sistema.

Opzione 2:confronta con i caratteri reali

Un'altra opzione è usare il LIKE operatore e specificare i caratteri maiuscoli effettivi che vogliamo abbinare:

SELECT c1 FROM t1
WHERE c1 LIKE '%[ABCDEFGHIJKLMNOPQRSTUVWXYZ]%'
COLLATE Latin1_General_CS_AS;

Risultato:

+----------------+
| c1             |
|----------------|
| CAFÉ           |
| Café           |
| eCafé          |
| James Bond 007 |
| JB 007         |
+----------------+

In questo caso, vengono restituite meno righe rispetto all'esempio precedente. Questo perché non ho specificato caratteri come É e Ø , restituiti nell'esempio precedente. Il nostro risultato contiene É ma quella riga è stata restituita solo perché contiene anche altri caratteri maiuscoli che fa corrispondenza.

Pertanto, questa opzione è più limitata della precedente, ma ti offre un maggiore controllo sui personaggi che desideri abbinare.

Opzione 3:confronta con un intervallo di caratteri

Possiamo in alternativa specificare l'intervallo di caratteri che vogliamo abbinare:

SELECT * FROM t1
WHERE c1 LIKE '%[A-Z]%'
COLLATE Latin1_General_100_BIN2;

Risultato:

+----------------+
| c1             |
|----------------|
| CAFÉ           |
| Café           |
| eCafé          |
| James Bond 007 |
| JB 007         |
+----------------+

In questo caso, ho usato un confronto binario (Latin1_General_100_BIN2 ). L'ho fatto perché le regole di confronto binarie ordinano ogni caso separatamente (come questo:AB....YZ...ab...yz ).

Altre regole di confronto tendono a mescolare le lettere maiuscole e minuscole (come questa:AaBb...YyZz ), che quindi corrisponderebbe sia ai caratteri maiuscoli che a quelli minuscoli.

Opzione 4:trova la prima istanza di un carattere maiuscolo

Un altro modo per farlo è usare PATINDEX() funzione:

SELECT * FROM t1
WHERE PATINDEX('%[ABCDEFGHIJKLMNOPQRSTUVWXYZ]%', c1
COLLATE Latin1_General_CS_AS) > 0;

Risultato:

+----------------+
| c1             |
|----------------|
| CAFÉ           |
| Café           |
| eCafé          |
| James Bond 007 |
| JB 007         |
+----------------+

In questo esempio, specifichiamo i caratteri esatti che vogliamo far corrispondere, quindi in questo caso non abbiamo ottenuto le righe con i caratteri like É e Ø (diverso da quello che contiene anche altri caratteri che sono stati abbinati).

Un vantaggio di questa tecnica è che possiamo usarla per ignorare il primo carattere (o il numero specificato di caratteri) se lo desideriamo:

SELECT * FROM t1
WHERE PATINDEX('%[ABCDEFGHIJKLMNOPQRSTUVWXYZ]%', c1
COLLATE Latin1_General_CS_AS) > 1;

Risultato:

Time: 0.472s
+-------+
| c1    |
|-------|
| eCafé |
+-------+

Pertanto, possiamo restituire tutte le righe che contengono caratteri maiuscoli, ma in cui il primo carattere non è maiuscolo.

Questo perché PATINDEX() restituisce la posizione iniziale della prima occorrenza del pattern (nel nostro caso, il pattern è un elenco di caratteri maiuscoli). Se la posizione iniziale della prima occorrenza è maggiore di 1, il primo carattere non è nel nostro elenco di caratteri maiuscoli.

Opzione 5:trova la prima istanza in base a un intervallo

Possiamo anche usare PATINDEX() con un intervallo:

SELECT * FROM t1
WHERE PATINDEX('%[A-Z]%', c1
COLLATE Latin1_General_100_BIN2) > 1;

Risultato:

+-------+
| c1    |
|-------|
| eCafé |
+-------+

Ho usato di nuovo un confronto binario (come con l'altro esempio di intervallo).