Como trabalhar com resultados de pesquisa no Azure AI Search

Este artigo explica como trabalhar com uma resposta de consulta no Azure AI Search. A estrutura de uma resposta é determinada por parâmetros na própria consulta, conforme descrito em Documentos de Pesquisa (REST) ou Classe SearchResults (Azure para .NET).

Os parâmetros na consulta determinam:

  • Seleção de campo
  • Contagem de correspondências encontradas no índice da consulta
  • Resultados de paginação
  • Número de resultados na resposta (até 50, por padrão)
  • Sequência de ordenação
  • Destaque de termos dentro de um resultado, combinando no termo total ou parcial no corpo

Composição dos resultados

Os resultados são tabulares, compostos por campos de todos os campos "recuperáveis" ou limitados apenas aos campos especificados nos $select parâmetros. As linhas são os documentos correspondentes.

Você pode escolher quais campos estão nos resultados da pesquisa. Embora um documento de pesquisa possa ter um grande número de campos, normalmente apenas alguns são necessários para representar cada documento nos resultados. Em uma solicitação de consulta, acrescente $select=<field list> para especificar quais campos "recuperáveis" devem aparecer na resposta.

Escolha campos que ofereçam contraste e diferenciação entre documentos, fornecendo informações suficientes para convidar uma resposta de clique por parte do usuário. Em um site de comércio eletrônico, pode ser um nome de produto, descrição, marca, cor, tamanho, preço e classificação. Para o índice de amostra de hotéis incorporado, podem ser os campos "select" no exemplo seguinte:

POST /indexes/hotels-sample-index/docs/search?api-version=2020-06-30 
    {  
      "search": "sandy beaches",
      "select": "HotelId, HotelName, Description, Rating, Address/City"
      "count": true
    }

Nota

Para imagens em resultados, como uma foto ou logotipo de produto, armazene-as fora do Azure AI Search, mas adicione um campo em seu índice para fazer referência à URL da imagem no documento de pesquisa. Os índices de exemplo que demonstram imagens nos resultados incluem a demonstração realestate-sample-us (um conjunto de dados de exemplo interno que você pode criar facilmente no assistente Importar dados) e o aplicativo de demonstração New York City Jobs.

Dicas para resultados inesperados

Ocasionalmente, a substância e não a estrutura dos resultados são inesperadas. Por exemplo, você pode achar que alguns resultados parecem ser duplicados ou um resultado que deve aparecer perto da parte superior está posicionado abaixo nos resultados. Quando os resultados da consulta são inesperados, você pode tentar estas modificações de consulta para ver se os resultados melhoram:

  • Altere searchMode=any (padrão) para searchMode=all exigir correspondências em todos os critérios em vez de qualquer um dos critérios. Isso é especialmente verdadeiro quando operadores booleanos são incluídos na consulta.

  • Experimente diferentes analisadores lexicais ou analisadores personalizados para ver se isso altera o resultado da consulta. O analisador padrão quebrará palavras hifenizadas e reduzirá palavras a formas raiz, o que geralmente melhora a robustez de uma resposta de consulta. No entanto, se você precisar preservar hífenes ou se as cadeias de caracteres incluírem caracteres especiais, talvez seja necessário configurar analisadores personalizados para garantir que o índice contenha tokens no formato correto. Para obter mais informações, consulte Pesquisa parcial de termos e padrões com caracteres especiais (hífenes, curinga, regex, padrões).

Contagem de jogos

O parâmetro count retorna o número de documentos no índice que são considerados uma correspondência para a consulta. Para retornar a contagem, adicione $count=true à solicitação de consulta. Não há um valor máximo imposto pelo serviço de pesquisa. Dependendo da sua consulta e do conteúdo dos seus documentos, a contagem pode ser tão alta quanto todos os documentos do índice.

A contagem é precisa quando o índice é estável. Se o sistema estiver ativamente adicionando, atualizando ou excluindo documentos, a contagem será aproximada, excluindo todos os documentos que não estão totalmente indexados.

A contagem não será afetada pela manutenção de rotina ou outras cargas de trabalho no serviço de pesquisa. No entanto, se você tiver várias partições e uma única réplica, poderá experimentar flutuações de curto prazo na contagem de documentos (vários minutos) à medida que as partições são reiniciadas.

Gorjeta

Para verificar as operações de indexação, você pode confirmar se o índice contém o número esperado de documentos adicionando $count=true uma consulta de pesquisa search=* vazia. O resultado é a contagem completa de documentos no seu índice.

Ao testar a sintaxe da consulta, $count=true você pode dizer rapidamente se suas modificações estão retornando resultados maiores ou menores, o que pode ser um feedback útil.

Resultados de paginação

Por padrão, o mecanismo de pesquisa retorna até as primeiras 50 correspondências. Os 50 primeiros são determinados pela pontuação da pesquisa, assumindo que a consulta é pesquisa de texto completo ou semântica. Caso contrário, os 50 primeiros são uma ordem arbitrária para consultas de correspondência exata (onde o uniforme "@searchScore=1.0" indica classificação arbitrária).

Para controlar a paginação de todos os documentos retornados em um conjunto de resultados, adicione $top parâmetros e $skip à solicitação de consulta GET ou top e skip à solicitação de consulta POST. A lista a seguir explica a lógica.

  • Devolve o primeiro conjunto de 15 documentos correspondentes mais uma contagem do total de correspondências: GET /indexes/<INDEX-NAME>/docs?search=<QUERY STRING>&$top=15&$skip=0&$count=true

  • Devolva o segundo set, pulando os primeiros 15 para obter os próximos 15: $top=15&$skip=15. Repita para o terceiro conjunto de 15: $top=15&$skip=30

Não é garantido que os resultados das consultas paginadas sejam estáveis se o índice subjacente estiver mudando. A paginação altera o valor de $skip cada página, mas cada consulta é independente e opera na exibição atual dos dados tal como existem no índice no momento da consulta (em outras palavras, não há cache ou instantâneo de resultados, como os encontrados em um banco de dados de uso geral).

A seguir está um exemplo de como você pode obter duplicatas. Suponha um índice com quatro documentos:

{ "id": "1", "rating": 5 }
{ "id": "2", "rating": 3 }
{ "id": "3", "rating": 2 }
{ "id": "4", "rating": 1 }

Agora suponha que você queira que os resultados retornem dois de cada vez, ordenados por classificação. Você executaria esta consulta para obter a primeira página de resultados: $top=2&$skip=0&$orderby=rating desc, produzindo os seguintes resultados:

{ "id": "1", "rating": 5 }
{ "id": "2", "rating": 3 }

No serviço, suponha que um quinto documento seja adicionado ao índice entre as chamadas de consulta: { "id": "5", "rating": 4 }. Pouco tempo depois, você executa uma consulta para buscar a segunda página: $top=2&$skip=2&$orderby=rating desc, e obtém estes resultados:

{ "id": "2", "rating": 3 }
{ "id": "3", "rating": 2 }

Observe que o documento 2 é buscado duas vezes. Isso ocorre porque o novo documento 5 tem um valor maior para classificação, então ele classifica antes do documento 2 e pousa na primeira página. Embora esse comportamento possa ser inesperado, é típico de como um mecanismo de pesquisa se comporta.

Paginação através de um grande número de resultados

Usar $top e $skip permitir que uma consulta de pesquisa percorra 100.000 resultados, mas e se os resultados forem maiores que 100.000? Para percorrer uma resposta tão grande, use um filtro de ordem de classificação e intervalo como solução alternativa para $skipo .

Nesta solução alternativa, a classificação e o filtro são aplicados a um campo ID do documento ou a outro campo exclusivo para cada documento. O campo exclusivo deve ter filterable e sortable atribuição no índice de pesquisa.

  1. Emita uma consulta para retornar uma página inteira de resultados classificados.

    POST /indexes/good-books/docs/search?api-version=2020-06-30
        {  
          "search": "divine secrets",
          "top": 50,
          "orderby": "id asc"
        }
    
  2. Escolha o último resultado retornado pela consulta de pesquisa. Um exemplo de resultado com apenas um valor "id" é mostrado aqui.

    {
        "id": "50"
    }
    
  3. Use esse valor "id" em uma consulta de intervalo para buscar a próxima página de resultados. Este campo "id" deve ter valores exclusivos, caso contrário, a paginação pode incluir resultados duplicados.

    POST /indexes/good-books/docs/search?api-version=2020-06-30
        {  
          "search": "divine secrets",
          "top": 50,
          "orderby": "id asc",
          "filter": "id ge 50"
        }
    
  4. A paginação termina quando a consulta retorna resultados zero.

Nota

Os atributos "filtrável" e "classificável" só podem ser habilitados quando um campo é adicionado pela primeira vez a um índice, eles não podem ser habilitados em um campo existente.

Ordenar resultados

Numa consulta de pesquisa de texto completo, os resultados podem ser classificados por:

  • uma pontuação de pesquisa
  • uma pontuação de reclassificação semântica
  • Uma ordem de classificação em um campo "classificável"

Você também pode impulsionar todas as partidas encontradas em campos específicos adicionando um perfil de pontuação.

Ordenar por pontuação de pesquisa

Para consultas de pesquisa de texto completo, os resultados são automaticamente classificados por uma pontuação de pesquisa, calculada com base na frequência do termo e na proximidade de um documento (derivada do TF-IDF), com pontuações mais altas indo para documentos com correspondências mais ou mais fortes em um termo de pesquisa.

O intervalo "@search.score" é ilimitado ou 0 até (mas não incluindo) 1,00 em serviços mais antigos.

Para qualquer um dos algoritmos, um "@search.score" igual a 1.00 indica um conjunto de resultados não pontuado ou não classificado, onde a pontuação de 1.0 é uniforme em todos os resultados. Os resultados não pontuados ocorrem quando o formulário de consulta é uma pesquisa difusa, consultas curinga ou regex ou uma pesquisa vazia (search=*). Se você precisar impor uma estrutura de classificação sobre resultados não pontuados, considere uma $orderby expressão para alcançar esse objetivo.

Ordem pelo reclassificador semântico

Se você estiver usando a classificação semântica, o "@search.rerankerScore" determinará a ordem de classificação dos resultados.

O intervalo "@search.rerankerScore" é de 1 a 4,00, onde uma pontuação mais alta indica uma correspondência semântica mais forte.

Encomende com $orderby

Se a ordenação consistente for um requisito do aplicativo, você poderá definir uma $orderby expressão em um campo. Somente os campos indexados como "classificáveis" podem ser usados para ordenar os resultados.

Os campos normalmente usados em um $orderby incluem classificação, data e local. A filtragem por local requer que a expressão de filtro chame a geo.distance() função, além do nome do campo.

Os campos numéricos (Edm.Double, Edm.Int32, Edm.Int64) são classificados em ordem numérica (por exemplo, 1, 2, 10, 11, 20).

Os campos de cadeia de caracteres (subcampos Edm.String, Edm.ComplexType) são classificados em ordem de classificação ASCII ou ordem de classificação Unicode, dependendo do idioma. Não é possível classificar coleções de qualquer tipo.

  • O conteúdo numérico nos campos de cadeia de caracteres é ordenado alfabeticamente (1, 10, 11, 2, 20).

  • As cordas maiúsculas são classificadas à frente das minúsculas (APPLE, Apple, BANANA, Banana, apple, banana). Você pode atribuir um normalizador de texto para pré-processar o texto antes de classificar para alterar esse comportamento. Usar o tokenizador minúsculo em um campo não terá efeito no comportamento de classificação porque o Azure AI Search classifica em uma cópia não analisada do campo.

  • Cordas que conduzem com diacríticos aparecem por último (Äpfel, Öffnen, Üben)

Aumente a relevância usando um perfil de pontuação

Outra abordagem que promove a consistência da ordem é o uso de um perfil de pontuação personalizado. Os perfis de pontuação dão mais controle sobre a classificação dos itens nos resultados de pesquisa, com a capacidade de aumentar as correspondências encontradas em campos específicos. A lógica de pontuação extra pode ajudar a substituir pequenas diferenças entre réplicas porque as pontuações de pesquisa de cada documento estão mais distantes. Recomendamos o algoritmo de classificação para esta abordagem.

Detetor de ocorrências

O realce de cliques refere-se à formatação de texto (como realces em negrito ou amarelo) aplicada a termos correspondentes em um resultado, facilitando a identificação da correspondência. O realce é útil para campos de conteúdo mais longos, como um campo de descrição, onde a correspondência não é imediatamente óbvia.

Observe que o realce é aplicado a termos individuais. Não há capacidade de destaque para o conteúdo de um campo inteiro. Se quiser realçar uma frase, terá de fornecer os termos (ou frases) correspondentes numa cadeia de consulta entre aspas. Esta técnica é descrita mais adiante nesta seção.

As instruções de realce de cliques são fornecidas na solicitação de consulta. As consultas que acionam a expansão da consulta no mecanismo, como a pesquisa difusa e curinga, têm suporte limitado para realce de acertos.

Requisitos para realce de hit

  • Os campos devem ser Edm.String ou Collection(Edm.String)
  • Os campos devem ser atribuídos em pesquisável

Especificar realce no pedido

Para retornar termos realçados, inclua o parâmetro "highlight" na solicitação de consulta. O parâmetro é definido como uma lista delimitada por vírgulas de campos.

Por padrão, a marcação de formato é <em>, mas você pode substituir a tag usando highlightPreTag e highlightPostTag parâmetros. O código do cliente lida com a resposta (por exemplo, aplicando uma fonte em negrito ou um plano de fundo amarelo).

POST /indexes/good-books/docs/search?api-version=2020-06-30 
    {  
      "search": "divine secrets",  
      "highlight": "title, original_title",
      "highlightPreTag": "<b>",
      "highlightPostTag": "</b>"
    }

Por padrão, o Azure AI Search retorna até cinco destaques por campo. Você pode ajustar esse número acrescentando um traço seguido de um inteiro. Por exemplo, "highlight": "description-10" retorna até 10 termos realçados no conteúdo correspondente no campo "descrição".

Resultados em destaque

Quando o realce é adicionado à consulta, a resposta inclui um "@search.highlights" para cada resultado para que o código do aplicativo possa direcionar essa estrutura. A lista de campos especificados para "destaque" é incluída na resposta.

Em uma pesquisa por palavra-chave, cada termo é verificado de forma independente. Uma consulta por "segredos divinos" retornará correspondências em qualquer documento que contenha qualquer um dos termos.

Captura de ecrã a mostrar o realce sobre uma consulta de frase.

Realce da pesquisa por palavra-chave

Dentro de um campo realçado, a formatação é aplicada a termos inteiros. Por exemplo, em uma partida contra "Os Segredos Divinos da Irmandade Ya-Ya", a formatação é aplicada a cada termo separadamente, mesmo que eles sejam consecutivos.

"@odata.count": 39,
"value": [
    {
        "@search.score": 19.593246,
        "@search.highlights": {
            "original_title": [
                "<em>Divine</em> <em>Secrets</em> of the Ya-Ya Sisterhood"
            ],
            "title": [
                "<em>Divine</em> <em>Secrets</em> of the Ya-Ya Sisterhood"
            ]
        },
        "original_title": "Divine Secrets of the Ya-Ya Sisterhood",
        "title": "Divine Secrets of the Ya-Ya Sisterhood"
    },
    {
        "@search.score": 12.779835,
        "@search.highlights": {
            "original_title": [
                "<em>Divine</em> Madness"
            ],
            "title": [
                "<em>Divine</em> Madness (Cherub, #5)"
            ]
        },
        "original_title": "Divine Madness",
        "title": "Divine Madness (Cherub, #5)"
    },
    {
        "@search.score": 12.62534,
        "@search.highlights": {
            "original_title": [
                "Grave <em>Secrets</em>"
            ],
            "title": [
                "Grave <em>Secrets</em> (Temperance Brennan, #5)"
            ]
        },
        "original_title": "Grave Secrets",
        "title": "Grave Secrets (Temperance Brennan, #5)"
    }
]

Realce da pesquisa de frases

A formatação de termo completo aplica-se mesmo numa pesquisa de frases, em que vários termos são colocados entre aspas duplas. O exemplo a seguir é a mesma consulta, exceto que "segredos divinos" é enviado como uma frase entre aspas (alguns clientes REST exigem que você escape das aspas interiores com uma barra \"invertida):

POST /indexes/good-books/docs/search?api-version=2020-06-30 
    {  
      "search": "\"divine secrets\"",,
      "select": "title,original_title",
      "highlight": "title",
      "highlightPreTag": "<b>",
      "highlightPostTag": "</b>",
      "count": true
    }

Como o critério agora tem os dois termos, apenas uma correspondência é encontrada no índice de pesquisa. A resposta à consulta acima tem esta aparência:

{
    "@odata.count": 1,
    "value": [
        {
            "@search.score": 19.593246,
            "@search.highlights": {
                "title": [
                    "<b>Divine</b> <b>Secrets</b> of the Ya-Ya Sisterhood"
                ]
            },
            "original_title": "Divine Secrets of the Ya-Ya Sisterhood",
            "title": "Divine Secrets of the Ya-Ya Sisterhood"
        }
    ]
}

Destaque da frase em serviços mais antigos

Os serviços de pesquisa criados antes de 15 de julho de 2020 implementam uma experiência de realce diferente para consultas de frase.

Para os exemplos a seguir, suponha uma cadeia de caracteres de consulta que inclua a frase entre aspas "super bowl". Antes de julho de 2020, qualquer termo da frase é destacado:

"@search.highlights": {
    "sentence": [
        "The <em>super</em> <em>bowl</em> is <em>super</em> awesome with a <em>bowl</em> of chips"
   ]

Para serviços de pesquisa criados após julho de 2020, apenas as frases que corresponderem à consulta de frase completa serão retornadas em "@search.highlights":

"@search.highlights": {
    "sentence": [
        "The <em>super</em> <em>bowl</em> is super awesome with a bowl of chips"
   ]

Próximos passos

Para gerar rapidamente uma página de pesquisa para o seu cliente, considere estas opções:

  • O Application Generator, no portal, cria uma página HTML com uma barra de pesquisa, navegação facetada e área de resultados que inclui imagens.

  • Adicionar pesquisa a um aplicativo ASP.NET Core (MVC) é um tutorial e um exemplo de código que cria um cliente funcional.

  • Adicionar pesquisa a aplicativos Web é um tutorial e um exemplo de código que usa as bibliotecas JavaScript do React para a experiência do usuário. O aplicativo é implantado usando os Aplicativos Web Estáticos do Azure.