Nach Einbettungen mit Vektorsuche suchen

In dieser Anleitung wird gezeigt, wie Sie mit der VECTOR_SEARCH Funktion und einem Vektorindex eine Ähnlichkeitssuche für Einbettungen durchführen, die in BigQuery-Tabellen gespeichert sind.

Die Vektorsuche ist eine Technik zum Vergleichen ähnlicher Objekte mithilfe von Einbettungen. Sie wird in Google-Produkten wie der Google Suche, YouTube und Google Play verwendet. Mit der Vektorsuche können Sie semantische Suchen im großen Maßstab durchführen oder eine hybride Suche ausführen, die eine semantische Suche mit einer lexikalischen (Keyword-)Suche kombiniert. Wenn Sie Vektorindizes mit der Vektorsuche verwenden, können Sie grundlegende Technologien wie die umgekehrte Dateiindizierung (Inverted File Indexing, IVF) und den ScaNN-Algorithmus nutzen.

Die Vektorsuche basiert auf Einbettungen. Einbettungen sind hochdimensionale numerische Vektoren, die eine bestimmte Entität darstellen, z. B. einen Text oder eine Audiodatei. Modelle für maschinelles Lernen (ML) verwenden Einbettungen, um semantische Informationen zu solchen Entitäten zu codieren, um die Verarbeitung und den Vergleich zu erleichtern. Eine häufige Operation in Clustering-, Klassifizierungs- und Empfehlungsmodellen ist beispielsweise das Messen der Distanz zwischen Vektoren in einem Einbettungsbereich, um Elemente zu finden, die semantisch am ähnlichsten sind.

Ziele

  • Eine Ähnlichkeitssuche für Einbettungen durchführen, die in BigQuery-Tabellen gespeichert sind, indem Sie die Funktion VECTOR_SEARCH verwenden.
  • Einen Vektorindex verwenden, um die Leistung der Vektorsuche zu verbessern.
  • Eine Suche mit einem Vektorindex und eine Suche ohne Index durchführen.
  • Den Recall bewerten, indem Sie die Ergebnisse von Suchen mit Index und Suchen ohne Index vergleichen.

Kosten

Für die VECTOR_SEARCH Funktion gelten die BigQuery-Preise für die Datenverarbeitung. Die Kosten für die Ähnlichkeitssuche werden nach den On-Demand-Preisen oder den Preisen für die Editionen berechnet.

  • On-Demand-Preise: Ihnen werden die Kosten für die Anzahl der Byte in Rechnung gestellt, die in der Basistabelle, im Index und in der Suchanfrage gescannt wurden.
  • Preise für Editionen: Ihnen werden die Slots in Rechnung gestellt, die erforderlich sind, um den Job innerhalb Ihrer reservierten Edition abzuschließen. Größere und komplexere Ähnlichkeitsberechnungen verursachen höhere Kosten.

Weitere Informationen finden Sie unter BigQuery-Preise.

Hinweis

  1. Wählen Sie in der Google Cloud Console auf der Seite für die Projektauswahl ein Projekt vonaus oder erstellen Sie eines Google Cloud .

    Erforderliche Rollen zum Auswählen oder Erstellen eines Projekts

    • Projekt auswählen: Für die Auswahl eines Projekts ist keine bestimmte IAM-Rolle erforderlich. Sie können ein beliebiges Projekt auswählen, für das Ihnen eine Rolle zugewiesen wurde.
    • Projekt erstellen: Zum Erstellen eines Projekts benötigen Sie die Rolle „Projektersteller“ (roles/resourcemanager.projectCreator), die die resourcemanager.projects.create Berechtigung enthält. Informationen zum Zuweisen von Rollen.

    Zur Projektauswahl

  2. Prüfen Sie, ob für Ihr Google Cloud Projekt die Abrechnung aktiviert ist.

  3. Aktivieren Sie die BigQuery API.

    Erforderliche Rollen zum Aktivieren von APIs

    Zum Aktivieren von APIs benötigen Sie die Berechtigung serviceusage.services.enable. Wenn Sie das Projekt erstellt haben, haben Sie diese Berechtigung wahrscheinlich bereits über die Rolle „Inhaber“ (roles/owner). Andernfalls können Sie diese Berechtigung über die Rolle „Service Usage-Administrator“ (roles/serviceusage.serviceUsageAdmin) erhalten. Informationen zum Zuweisen von Rollen.

    API aktivieren

Erforderliche Rollen

Bitten Sie Ihren Administrator, Ihnen die folgenden IAM-Rollen für Ihr Projekt zuzuweisen, um die Berechtigungen zu erhalten, die Sie zum Ausführen dieser Anleitung benötigen:

Weitere Informationen zum Zuweisen von Rollen finden Sie unter Zugriff auf Projekte, Ordner und Organisationen verwalten.

Sie können die erforderlichen Berechtigungen auch über benutzerdefinierte Rollen oder andere vordefinierte Rollen erhalten.

Dataset erstellen

Wählen Sie eine der folgenden Optionen aus, um ein BigQuery-Dataset zu erstellen:

Console

  1. Rufen Sie in der Google Cloud Console die Seite BigQuery auf.

    BigQuery aufrufen

  2. Klicken Sie im linken Bereich auf Explorer:

    Hervorgehobener Button für den Explorer-Bereich.

    Wenn der linke Bereich nicht angezeigt wird, klicken Sie auf Linken Bereich maximieren , um ihn zu öffnen.

  3. Maximieren Sie in Explorer Ihr Projekt und klicken Sie dann auf Datasets.

  4. Klicken Sie auf der Seite Datasets auf Dataset erstellen.

  5. Führen Sie im Bereich Dataset erstellen die folgenden Schritte aus:

    • Geben Sie unter Dataset-ID bqml_tutorial ein.

    • Wählen Sie unter Speicherort der Daten die Option USA aus.

    Übernehmen Sie die anderen Standardeinstellungen.

  6. Klicken Sie auf Dataset erstellen.

bq

Verwenden Sie den bq mk --dataset Befehl, um ein neues Dataset zu erstellen.

  1. Erstellen Sie ein Dataset mit dem Namen bqml_tutorial und legen Sie den Speicherort der Daten auf US fest:

    bq mk --dataset \
      --location=US \
      --description "BigQuery ML tutorial dataset." \
      bqml_tutorial
  2. Prüfen Sie, ob das Dataset erstellt wurde:

    bq ls

API

Rufen Sie die datasets.insert Methode mit einer definierten Dataset-Ressource auf:

{
  "datasetReference": {
     "datasetId": "bqml_tutorial"
  }
}

Tabellen zum Speichern von Daten und Einbettungen erstellen

In diesem Abschnitt erstellen Sie die Tabelle patents, die Patenteinbettungen enthält. Die Einbettungen basieren auf einer Teilmenge des öffentlichen Datasets Google Patentsuche. Außerdem erstellen Sie die Tabelle patents2, die eine Patenteinbettung enthält, um die nächsten Nachbarn zu finden.

Führen Sie die folgenden Schritte aus, um die Tabellen zu erstellen:

  1. Fügen Sie Folgendes in den Abfrageeditor ein und klicken Sie auf Ausführen, um die Tabelle patents zu erstellen:

    CREATE TABLE bqml_tutorial.patents AS
    SELECT * FROM `patents-public-data.google_patents_research.publications`
    WHERE ARRAY_LENGTH(embedding_v1) > 0
     AND publication_number NOT IN ('KR-20180122872-A')
    LIMIT 1000000;

    Sie erhalten eine Bestätigungsnachricht wie die folgende: This statement created a new table named patents.

  2. Fügen Sie Folgendes in den Abfrageeditor ein und klicken Sie auf Ausführen, um die patents2 Tabelle zu erstellen, die eine Patenteinbettung enthält, um die nächsten Nachbarn zu finden:

    CREATE TABLE bqml_tutorial.patents2 AS
    SELECT * FROM `patents-public-data.google_patents_research.publications`
    WHERE publication_number = 'KR-20180122872-A';

    Sie erhalten eine Bestätigungsnachricht wie die folgende: This statement created a new table named patents2.

Vektorindex erstellen

Wenn Sie VECTOR_SEARCH mit einem Vektorindex verwenden, nutzt VECTOR_SEARCH die Methode „Annäherung an den nächsten Nachbarn“ , um die Leistung der Vektorsuche zu verbessern. Der Kompromiss ist jedoch, dass der Recall reduziert wird und somit ungefähre Ergebnisse zurückgegeben werden. Ohne Vektorindex verwendet VECTOR_SEARCH die Brute-Force-Suche , um die Distanz für jeden Datensatz zu messen.

In diesem Abschnitt erstellen Sie den Vektorindex my_index für die Spalte embedding_v1 der Tabelle patents. Anschließend prüfen Sie, ob der Index verfügbar ist.

Führen Sie die folgenden Schritte aus, um den Vektorindex zu erstellen:

  1. Fügen Sie Folgendes in den Abfrageeditor ein und klicken Sie auf Ausführen , um den my_index Vektorindex für die Spalte embedding_v1 der patents Tabelle zu erstellen:

    CREATE OR REPLACE VECTOR INDEX my_index ON bqml_tutorial.patents(embedding_v1)
    STORING(publication_number, title)
    OPTIONS(distance_type='COSINE', index_type='IVF');

    Sie erhalten eine Bestätigungsnachricht wie die folgende: The vector index creation on table bqml_tutorial.patents was initiated. Please query bqml_tutorial.INFORMATION_SCHEMA.VECTOR_INDEXES to check the progress of the index.

  2. Fügen Sie Folgendes in den Abfrage editor ein und klicken Sie auf Ausführen, um zu bestätigen, dass der Vektorindex bereit ist:

    SELECT * FROM bqml_tutorial.INFORMATION_SCHEMA.VECTOR_INDEXES;

    Prüfen Sie in den Abfrageergebnissen, ob index_status auf ACTIVE und coverage_percentage auf 100 gesetzt ist. Es kann einige Minuten dauern, bis coverage_percentage den Wert 100 erreicht.

Funktion VECTOR_SEARCH mit einem Index verwenden

Nachdem der Vektorindex erstellt und ausgefüllt wurde, verwenden Sie die Funktion VECTOR_SEARCH, um den nächsten Nachbarn für die Einbettung in der Spalte embedding_v1 der Tabelle patents2 zu finden. Diese Abfrage verwendet den Vektorindex in der Suche, daher verwendet VECTOR_SEARCH eine Methode „Annäherung an den nächsten Nachbarn“, um den nächsten Nachbarn der Einbettung zu finden.

Fügen Sie Folgendes in den Abfrageeditor ein und klicken Sie auf Ausführen, um die VECTOR_SEARCH Funktion mit einem Index zu verwenden:

SELECT query.publication_number AS query_publication_number,
  query.title AS query_title,
  base.publication_number AS base_publication_number,
  base.title AS base_title,
  distance
FROM
  VECTOR_SEARCH(
    TABLE bqml_tutorial.patents,
    'embedding_v1',
    TABLE bqml_tutorial.patents2,
    top_k => 5,
    distance_type => 'COSINE',
    options => '{"fraction_lists_to_search": 0.005}');

Das Ergebnis sieht in etwa so aus:

+--------------------------+-------------------------------------------------------------+-------------------------+--------------------------------------------------------------------------------------------------------------------------+---------------------+
| query_publication_number |                         query_title                         | base_publication_number |                                                        base_title                                                        |      distance       |
+--------------------------+-------------------------------------------------------------+-------------------------+--------------------------------------------------------------------------------------------------------------------------+---------------------+
| KR-20180122872-A         | Rainwater management system based on rainwater keeping unit | CN-106599080-B          | A kind of rapid generation for keeping away big vast transfer figure based on GIS                                        | 0.14471956347590609 |
| KR-20180122872-A         | Rainwater management system based on rainwater keeping unit | CN-114118544-A          | Urban waterlogging detection method and device                                                                           | 0.17472108931171348 |
| KR-20180122872-A         | Rainwater management system based on rainwater keeping unit | KR-20200048143-A        | Method and system for mornitoring dry stream using unmanned aerial vehicle                                               | 0.17561990745619782 |
| KR-20180122872-A         | Rainwater management system based on rainwater keeping unit | KR-101721695-B1         | Urban Climate Impact Assessment method of Reflecting Urban Planning Scenarios and Analysis System using the same         | 0.17696129365559843 |
| KR-20180122872-A         | Rainwater management system based on rainwater keeping unit | CN-109000731-B          | The experimental rig and method that research inlet for stom water chocking-up degree influences water discharged amount | 0.17902723269642917 |
+--------------------------+-------------------------------------------------------------+-------------------------+--------------------------------------------------------------------------------------------------------------------------+---------------------+

Funktion VECTOR_SEARCH mit Brute-Force verwenden

In diesem Abschnitt verwenden Sie die Funktion VECTOR_SEARCH, um den nächsten Nachbarn für die Einbettung in der Spalte embedding_v1 der Tabelle patents2 zu finden. Diese Abfrage verwendet den Vektorindex nicht in der Suche, sodass VECTOR_SEARCH den genauen nächsten Nachbarn der Einbettung findet.

Fügen Sie Folgendes in den Abfrage editor ein und klicken Sie auf Ausführen, um VECTOR_SEARCH mit Brute-Force zu verwenden:

SELECT query.publication_number AS query_publication_number,
  query.title AS query_title,
  base.publication_number AS base_publication_number,
  base.title AS base_title,
  distance
FROM
  VECTOR_SEARCH(
    TABLE bqml_tutorial.patents,
    'embedding_v1',
    TABLE bqml_tutorial.patents2,
    top_k => 5,
    distance_type => 'COSINE',
    options => '{"use_brute_force":true}');

Das Ergebnis sieht in etwa so aus:

+--------------------------+-------------------------------------------------------------+-------------------------+--------------------------------------------------------------------------------------------------------------------------+---------------------+
| query_publication_number |                         query_title                         | base_publication_number |                                                        base_title                                                        |      distance       |
+--------------------------+-------------------------------------------------------------+-------------------------+--------------------------------------------------------------------------------------------------------------------------+---------------------+
| KR-20180122872-A         | Rainwater management system based on rainwater keeping unit | CN-106599080-B          | A kind of rapid generation for keeping away big vast transfer figure based on GIS                                        |  0.1447195634759062 |
| KR-20180122872-A         | Rainwater management system based on rainwater keeping unit | CN-114118544-A          | Urban waterlogging detection method and device                                                                           |  0.1747210893117136 |
| KR-20180122872-A         | Rainwater management system based on rainwater keeping unit | KR-20200048143-A        | Method and system for mornitoring dry stream using unmanned aerial vehicle                                               | 0.17561990745619782 |
| KR-20180122872-A         | Rainwater management system based on rainwater keeping unit | KR-101721695-B1         | Urban Climate Impact Assessment method of Reflecting Urban Planning Scenarios and Analysis System using the same         | 0.17696129365559843 |
| KR-20180122872-A         | Rainwater management system based on rainwater keeping unit | CN-109000731-B          | The experimental rig and method that research inlet for stom water chocking-up degree influences water discharged amount | 0.17902723269642928 |
+--------------------------+-------------------------------------------------------------+-------------------------+--------------------------------------------------------------------------------------------------------------------------+---------------------+

Recall bewerten

Wenn Sie eine Vektorsuche mit einem Index ausführen, werden ungefähre Ergebnisse zurückgegeben, aber der Recall wird reduziert. Zur Berechnung des Recalls können Sie die von der Vektorsuche zurückgegebenen Ergebnisse mit einem Index und die Vektorsuche mit Brute-Force vergleichen. Der Wert publication_number identifiziert ein Patent eindeutig. Daher wird er in der folgenden Abfrage zum Vergleich verwendet.

Fügen Sie Folgendes in den Abfrageeditor ein und klicken Sie auf Ausführen , um den Recall zu bewerten:

WITH approx_results AS (
  SELECT query.publication_number AS query_publication_number,
    base.publication_number AS base_publication_number
  FROM
    VECTOR_SEARCH(
      TABLE bqml_tutorial.patents,
      'embedding_v1',
      TABLE bqml_tutorial.patents2,
      top_k => 5,
      distance_type => 'COSINE',
      options => '{"fraction_lists_to_search": 0.005}')
),
  exact_results AS (
  SELECT query.publication_number AS query_publication_number,
    base.publication_number AS base_publication_number
  FROM
    VECTOR_SEARCH(
      TABLE bqml_tutorial.patents,
      'embedding_v1',
      TABLE bqml_tutorial.patents2,
      top_k => 5,
      distance_type => 'COSINE',
      options => '{"use_brute_force":true}')
)

SELECT
  a.query_publication_number,
  SUM(CASE WHEN a.base_publication_number = e.base_publication_number THEN 1 ELSE 0 END) / 5 AS recall
FROM exact_results e LEFT JOIN approx_results a
  ON e.query_publication_number = a.query_publication_number
GROUP BY a.query_publication_number;

Das Ergebnis sieht in etwa so aus:

+--------------------------+--------+
| query_publication_number | recall |
+--------------------------+--------+
| KR-20180122872-A         |    1.0 |
+--------------------------+--------+

Wenn der Recall niedriger als gewünscht ist, können Sie den Wert fraction_lists_to_search erhöhen. Dies kann jedoch zu einer potenziell höheren Latenz und Ressourcennutzung führen. Zur Optimierung Ihrer Vektorsuche können Sie mehrere Ausführungen von VECTOR_SEARCH mit unterschiedlichen Argumentwerten testen, die Ergebnisse in Tabellen speichern und dann die Ergebnisse vergleichen.

Bereinigen

Damit Ihrem Google Cloud-Konto die in dieser Anleitung verwendeten Ressourcen nicht in Rechnung gestellt werden, löschen Sie entweder das Projekt, das die Ressourcen enthält, oder Sie behalten das Projekt und löschen die einzelnen Ressourcen.

  1. Wechseln Sie in der Google Cloud Console zur Seite Ressourcen verwalten.

    Zur Seite „Ressourcen verwalten“

  2. Wählen Sie in der Projektliste das Projekt aus, das Sie löschen möchten, und klicken Sie auf Löschen.
  3. Geben Sie im Dialogfeld die Projekt-ID ein und klicken Sie auf Shut down (Herunterfahren), um das Projekt zu löschen.

Wenn Sie das Projekt beibehalten und die in dieser Anleitung verwendeten Ressourcen löschen möchten, führen Sie die folgenden Schritte aus:

  1. Rufen Sie die Seite BigQuery auf.

    BigQuery aufrufen

  2. Maximieren Sie im linken Bereich Ihr Projekt und klicken Sie dann auf Datasets.

  3. Klicken Sie für das Dataset bqml_tutorial auf Weitere Aktionen > Löschen.

  4. Klicken Sie im Dialogfeld Dataset löschen zur Bestätigung auf Löschen.

Nächste Schritte