2010-11-19 14 views
5

Ho bisogno di pulire i numeri di telefono memorizzati come varchar. Vi sono dati errati in cui i numeri di telefono sconosciuti sono memorizzati come una sequenza di una singola cifra. Eventualmente più complesso (prefisso prefisso & prefisso) verrà eseguito ma voglio semplicemente eseguire una query su record ovviamente non validi.Query T-SQL per identificare i campi varchar costituiti da un singolo carattere/cifra ripetuta?

Così, per esempio:

Valido Numero di telefono: 3289903829

valida Numero di telefono: 1111111111

Ora, se il numero di serie fasullo siano di lunghezza adeguata (10 cifre) è facile da analizzare e pulito.

SELECT phone 
    FROM customers 
    SET phone = NULL 
    WHERE phone IN ('0000000000','9999999999',''8888888888','7777777777','6666666666','5555555555','4444444444','3333333333','2222222222','1111111111') 

Tuttavia a volte i telefoni falsi sono di lunghezza arbitraria (probabilmente a causa di errori di battitura) così 11 quelli o 9, o quelli n quelli.
Come posso identificare le stringhe che contengono tutti lo stesso carattere/cifra?

1111111 - match 
4444 - match 
1112 - no match 
4445555 - no match 

risposta

10

È possibile ottenere il primo carattere e replicarlo:

where phone = replicate(left(phone,1), len(phone)) 
    and phone is not null 
+3

È anche possibile utilizzare 'sinistra (telefono, 1)' piuttosto che 'sottostringa (telefono, 1,1)'. –

+0

@ Mark, grazie verrà aggiornato per il tuo commento –

+0

@adrift è rimasto (telefono, 1) più veloce di sottostringa (telefono, 1,1)? Solo curioso. –

1

forse si potrebbe creare una funzione SQL per fare questo.

penso che il coraggio di esso sarebbe simile a questa:

DECLARE @field varchar(10) 
SET @field = '11111' 

DECLARE @len INT 
SET @len = LEN(@field) 

DECLARE @counter INT 
SET @counter = 1 

DECLARE @firstChar VARCHAR(1) 
SET @firstChar = NULL 

DECLARE @currentChar VARCHAR(1) 
SET @currentChar = NULL 

DECLARE @allSameNumber BIT 
SET @allSameNumber = 1 

WHILE @counter <= @len AND @allSameNumber = 1 BEGIN 

    SET @currentChar = SUBSTRING(@field,@counter,1) 
    IF @firstChar IS NULL BEGIN 
     SET @firstChar = @currentChar 
    END 
    IF NOT ISNUMERIC(@currentChar) = 1 OR NOT @currentChar = @firstChar BEGIN 
     SET @allSameNumber = 0 
    END 
    SET @counter = @counter + 1 

END 

SELECT @allSameNumber 
+0

Detto questo, la soluzione di replica è molto più elegante! Probabilmente andrei con quello. – Brandon

3

A seconda di quanto velocemente avete bisogno di correre, l'altra opzione è quella di compilare una tabella temporanea e quindi unire il vostro numero di telefono su di esso . Se lo fai più volte, potresti addirittura creare una tabella reale in modo da non doverla ricreare ogni volta. Per renderlo più veloce puoi anche indicizzare il campo. Il tuo chilometraggio può variare a seconda del tempo necessario per essere confrontato con il numero di record che devi confrontare.

CREATE TABLE #Numbers 
(
    PhoneNumber VARCHAR(13) NOT NULL 
) 

DECLARE @run BIT 
SET @run = 1 

DECLARE @number INT 
SET @number = 1 

DECLARE @Counter INT 
SET @Counter = 1 

WHILE(@run = 1) 
BEGIN 

WHILE(@Counter < 13) 
BEGIN 
    INSERT INTO #Numbers 
    SELECT REPLICATE(@number,@counter) 

    SET @Counter = @Counter + 1 
END 


SET @Counter = 1 
SET @number = @number + 1 

IF(@number > 9) 
BEGIN 
    SET @run = 0 
END 

END 

SELECT * FROM Phone p JOIN #numbers n ON p.PhoneNumber = n.PhoneNumber 

In questo modo non è necessario ricalcolare il campo in cui si confronta il numero ogni volta.

+0

Poiché la lunghezza di questi numeri di telefono "speciali" varia, si dovrebbe fare una query 'selezionare max (len (telefono))' da usare al posto di '13'. –

+1

che è un buon punto, in realtà guarderei la lunghezza del campo nella tabella, in quanto tecnicamente un numero di telefono potrebbe cambiare e il numero di telefono più lungo potrebbe essere quello aggiornato. Guardando il tavolo, sai che non avrai un numero di telefono più lungo di quello. – kemiller2002

+0

Bella soluzione.+1 Sono andato con il metodo più semplice perché nel mio caso è una pulizia "una tantum". Inserirò vincoli per impedire dati non validi. Il tuo metodo sarebbe la soluzione migliore per qualcuno che ha bisogno di eseguire periodicamente il lavaggio dei dati. –

Problemi correlati