none
SQL - AVANÇADO (Verificando se dois textos são parecidos) RRS feed

  • Pergunta

  • Olá pessoal tenho um problema que pareçe ser um poco mais complexo em sql, preciso obter alguma "nota" para qual o nivel de indentidade entre dois textos:

    Exemplo:

    t1 = Rato Roma
    t2 = Cama Lama

    Grau de identidade entre eles é 0%

    Outro Exemplo:

    t1 = Rato Roma
    t2 = Rato Lama

    Grau de identidade é de 50%

    Não sei se isso exigiria algo de IA no comando, mais queria poder saber quando um texto é quase parecido com outro.

    quinta-feira, 10 de novembro de 2011 16:07

Todas as Respostas

  • Boa Tarde,

    Não há "dialeto" SQL que lhe responda isso. Normalmente esse tipo de pergunta é respondido com ferramentas de Data Quality para identificar o grau de semelhança entre algumas strings. No T-SQL não há referência que atenda essa necessidade específica (o SOUNDEX iria dar muito trabalho de programação). Você pode tentar no SSIS com os algoritmos Fuzzy (uma Fuzzy Lookup da vida) para ver se lhe atende. Não sei propriamente se ela irá implementar o mesmo algoritmo de "matching" que você definiu.

    [ ]s,

    Gustavo Maia Aguiar
    Blog: http://gustavomaiaaguiar.wordpress.com
    Vídeos: http://www.youtube.com/user/gmasql


    Classifique as respostas. O seu feedback é imprescindível
    quinta-feira, 10 de novembro de 2011 16:50
  • Jean,

    Particularmente este tipo de algoritmo esta além das funcionalidades como também da forma que o SQL Server poderá realizar um tratamento de dados, como destacado pelo Gustavo existe uma função Chamando Soundex que tem como finalidade realizar uma análise fonética de palavras e expressões no SQL Server o que pode trazer alguma similaridade com sua necessidade.

    Em relação as algoritmos de Fuzzy, isso esta bastante relacionado com a Lógica de Fuzzy(Fuzzy Logic), conceito utilizado em IA para análise e desenvolvimento de unidades de processamento inteligentes.

    No BIDs este componente pode trabalhar de forma parecida com a sua necessidade, mas não terá uma abrangência ideal, em alguns casos o resultado não estará próximo ao desejado.

    Veja abaixo um código de exemplo de utilização da função SOUNDEX:

    CREATE FUNCTION dbo.FUNC_FONETIZAR (@STR VARCHAR(5000), @CONSULTA CHAR(1))
    RETURNS VARCHAR(5000)
    AS
    BEGIN
    DECLARE
      @PARTICULA        VARCHAR(5000),
      @FONETIZADO       VARCHAR(5000),
      @FONETIZAR        CHAR(1),
      @AUX              VARCHAR(5000),
      @I                INT,
      @CONT             INT,
      @PREPOSICOES1     VARCHAR(1000),
      @PREPOSICOES2     VARCHAR(1000),
      @ALGROMANO1       VARCHAR(1000),
      @NUMERO1          VARCHAR(1000),
      @ALGROMANO2       VARCHAR(1000),
      @NUMERO2          VARCHAR(1000),
      @ALGROMANO3       VARCHAR(1000),
      @NUMERO3          VARCHAR(1000),
      @ALGARISMO        VARCHAR(1000),
      @ALGARISMOEXTENSO VARCHAR(1000),
      @LETRAS           VARCHAR(1000)

      SELECT @STR = dbo.FUNC_REMOVE_ACENTO(@STR)

      /*********************************************/
      IF @STR = ' H '
         SET @STR = ' AGA '

      SELECT @STR = dbo.FUNC_SOMENTE_LETRAS(@STR)

      /*ELIMINAR PALAVRAS ESPECIAIS*/
      SELECT @STR = REPLACE(@STR,' LTDA ',' ')

      /*ELIMINAR PREPOSICOES*/
      SET @PREPOSICOES1 = ' DE  DA  DO  AS  OS  AO  NA  NO '
      SET @PREPOSICOES2 = ' DOS  DAS  AOS  NAS  NOS  COM '

      SET @I = 1

      WHILE @I <= 32
      BEGIN
         SELECT @STR = REPLACE(@STR,SUBSTRING(@PREPOSICOES1,@I,4),' ')
         SET @I = @I + 4
      END

      SET @I = 1

      WHILE @I <= 30
      BEGIN
         SELECT @STR = REPLACE(@STR,SUBSTRING(@PREPOSICOES2,@I,5),' ')
         SET @I = @I + 5
      END

      /*CONVERTE ALGARISMO ROMANO PARA NUMERO*/
      SET @ALGROMANO1 = ' V  I '
      SET @NUMERO1    = ' 5  1 '
      SET @I = 1
      WHILE @I <= 6
      BEGIN
         SELECT @STR = REPLACE(@STR,SUBSTRING(@ALGROMANO1,@I,3),SUBSTRING(@NUMERO1,@I,3))
         SET @I = @I + 3
      END

      SET @ALGROMANO2 = ' IX  VI  IV  II '
      SET @NUMERO2    = '  9   6   4   2 '
      SET @I = 1
      WHILE @I <= 16
      BEGIN
         SELECT @STR = REPLACE(@STR,SUBSTRING(@ALGROMANO2,@I,4),SUBSTRING(@NUMERO2,@I+1,3))
         SET @I = @I + 4
      END

      SET @ALGROMANO3 = ' VII  III '
      SET @NUMERO3    = '   7    3 '
      SET @I = 1
      WHILE @I <= 10
      BEGIN
         SELECT @STR = REPLACE(@STR,SUBSTRING(@ALGROMANO3,@I,5),SUBSTRING(@NUMERO3,@I+2,3))
         SET @I = @I + 5
      END

      SELECT @STR = REPLACE(@STR,' X ',' 10 ')
      SELECT @STR = REPLACE(@STR,' VIII ',' 8 ')


      /*CONVERTE NUMERO PARA LITERAL*/
      SELECT @STR = REPLACE(@STR,'0','ZERO')
      SELECT @STR = REPLACE(@STR,'1','UM')
      SELECT @STR = REPLACE(@STR,'2','DOIS')
      SELECT @STR = REPLACE(@STR,'3','TRES')
      SELECT @STR = REPLACE(@STR,'4','QUATRO')
      SELECT @STR = REPLACE(@STR,'5','CINCO')
      SELECT @STR = REPLACE(@STR,'6','SEIS')
      SELECT @STR = REPLACE(@STR,'7','SETE')
      SELECT @STR = REPLACE(@STR,'8','OITO')
      SELECT @STR = REPLACE(@STR,'9','NOVE')


      /*********************************************/
      /*ELIMINAR PREPOSICOES E ARTIGOS*/
      SET @LETRAS = ' A  B  C  D  E  F  G  H  I  J  K  L  M  N  O  P  Q  R  S  T  U  V  X  Z  W  Y ';

      SET @I = 1
      WHILE @I <= 78
      BEGIN
         SELECT @STR = REPLACE(@STR,SUBSTRING(@ALGROMANO2,@I,3),' ')
         SET @I = @I + 3
      END


      SET @STR = LTRIM(@STR)
      SET @STR = RTRIM(@STR)

      SET @PARTICULA  = ''
      SET @FONETIZADO = ''

      SET @CONT = 1

      WHILE @CONT <= LEN(@STR)+1
      BEGIN
         IF @CONT < LEN(@STR) + 1
         BEGIN
            IF SUBSTRING(@STR,@CONT,1) <> ' '
            BEGIN
               SET @PARTICULA = @PARTICULA + SUBSTRING(@STR,@CONT,1)
               SET @FONETIZAR = '0'
            END
            ELSE
               SET @FONETIZAR = '1'
         END
         ELSE
            SET @FONETIZAR = '1'
         IF @FONETIZAR = '1'
         BEGIN
            SELECT @PARTICULA = dbo.FUNC_FONETIZAR_PARTICULA(@PARTICULA)
            SET @FONETIZADO = @FONETIZADO + ' ' + @PARTICULA
            SET @PARTICULA = ''
         END
         SET @CONT = @CONT + 1
      END

      SET @FONETIZADO = LTRIM(@FONETIZADO)
      SET @FONETIZADO = RTRIM(@FONETIZADO)


      /*PREPARA A STRING PARA UM LIKE*/
      IF @CONSULTA = '1'
      BEGIN
        SET @AUX = '%'

        SET @I = 1

        WHILE @I <= LEN(@FONETIZADO)
        BEGIN
           IF SUBSTRING(@FONETIZADO,@I,1) = ' '
             SET @AUX = @AUX + '% %'
           ELSE
             SET @AUX = @AUX + SUBSTRING(@FONETIZADO,@I,1)
           SET @I = @I + 1
        END

        IF SUBSTRING(@FONETIZADO,LEN(@FONETIZADO),1) <> '%'
           SET @AUX = @AUX + '%'

        SET @FONETIZADO = @AUX
      END
      IF @FONETIZADO = ''
         SET @FONETIZADO = NULL
     
      RETURN @FONETIZADO
     
    END
    GO


    Pedro Antonio Galvão Junior [MVP | Microsoft Evangelist | Microsoft Partner | Engenheiro de Softwares | Especialista em Banco de Dados | SorBR.Net | Professor Universitário | MSIT.com]
    quinta-feira, 10 de novembro de 2011 23:46