Catatan
Akses ke halaman ini memerlukan otorisasi. Anda dapat mencoba masuk atau mengubah direktori.
Akses ke halaman ini memerlukan otorisasi. Anda dapat mencoba mengubah direktori.
Peringatan
Fungsionalitas Penyimpanan Vektor Kernel Semantik saat ini dalam tahap kandidat rilis (RC), dan peningkatan yang memerlukan perubahan yang mengakibatkan gangguan mungkin masih terjadi dalam kondisi terbatas sebelum rilis.
Peringatan
Fungsionalitas Penyimpanan Vektor Kernel Semantik sedang dalam pratinjau, dan peningkatan yang memerlukan perubahan yang melanggar mungkin masih terjadi dalam keadaan terbatas sebelum rilis.
Petunjuk / Saran
Jika Anda mencari informasi tentang konektor Penyimpanan Memori versi lama, lihat halaman Penyimpanan Memori.
Database vektor memiliki banyak kasus penggunaan di berbagai domain dan aplikasi yang melibatkan pemrosesan bahasa alami (NLP), computer vision (CV), sistem rekomendasi (RS), dan area lain yang memerlukan pemahaman semantik dan pencocokan data.
Satu kasus penggunaan untuk menyimpan informasi dalam database vektor adalah mengaktifkan model bahasa besar (LLM) untuk menghasilkan respons yang lebih relevan dan koheren. Model bahasa besar sering menghadapi tantangan seperti menghasilkan informasi yang tidak akurat atau tidak relevan; tidak memiliki konsistensi faktual atau akal sehat; mengulangi atau bertentangan dengan diri mereka sendiri; menjadi bias atau menyinggung. Untuk membantu mengatasi tantangan ini, Anda dapat menggunakan database vektor untuk menyimpan informasi tentang berbagai topik, kata kunci, fakta, opini, dan/atau sumber yang terkait dengan domain atau genre yang Anda inginkan. Database vektor memungkinkan Anda menemukan subset informasi yang terkait dengan pertanyaan atau topik tertentu secara efisien. Anda kemudian dapat meneruskan informasi dari database vektor dengan permintaan Anda ke model bahasa besar Anda untuk menghasilkan konten yang lebih akurat dan relevan.
Misalnya, jika Anda ingin menulis posting blog tentang tren terbaru di AI, Anda dapat menggunakan database vektor untuk menyimpan informasi terbaru tentang topik itu dan meneruskan informasi bersama dengan permintaan ke LLM untuk menghasilkan posting blog yang memanfaatkan informasi terbaru.
Semantic Kernel dan .net menyediakan sebuah abstraksi untuk berinteraksi dengan Vector Stores serta daftar solusi siap pakai yang menerapkan abstraksi ini untuk berbagai database. Fitur termasuk membuat, mencantumkan, dan menghapus koleksi rekaman, dan mengunggah, mengambil, dan menghapus rekaman. Abstraksi memudahkan untuk bereksperimen dengan Vektor Store gratis atau yang dihosting secara lokal dan kemudian beralih ke layanan ketika perlu meningkatkan skala.
Implementasi langsung siap pakai dapat digunakan dengan Kernel Semantik, tetapi tidak bergantung pada tumpukan inti Kernel Semantik dan dapat digunakan secara mandiri sepenuhnya jika diperlukan. Kernel Semantik dengan implementasi yang disediakan disebut sebagai 'konektor'.
Pengambilan Augmented Generation (RAG) dengan Vector Stores
Abstraksi penyimpanan vektor adalah api tingkat rendah untuk menambahkan dan mengambil data dari penyimpanan vektor.
Semantic Kernel memiliki dukungan bawaan untuk menggunakan salah satu implementasi Vector Store untuk RAG.
Ini dicapai dengan membungkus IVectorSearchable<TRecord> dan mengeksposnya sebagai implementasi Pencarian Teks.
Petunjuk / Saran
Untuk mempelajari selengkapnya tentang cara menggunakan penyimpanan vektor untuk RAG, lihat Cara menggunakan Penyimpanan Vektor dengan Pencarian Teks Kernel Semantik.
Petunjuk / Saran
Untuk mempelajari selengkapnya tentang pencarian teks, lihat Apa itu Pencarian Teks Kernel Semantik?
Petunjuk / Saran
Untuk mempelajari selengkapnya tentang cara menambahkan RAG dengan cepat ke agen Anda lihat Menambahkan Retrieval Augmented Generation (RAG) ke Agen Kernel Semantik.
Abstraksi Penyimpanan Vektor
Abstraksi Vector Store disediakan dalam Microsoft.Extensions.VectorData.Abstractions paket nuget.
Berikut ini adalah kelas dasar abstrak utama dan antarmuka.
Microsoft.Extensions.VectorData.VectorStore
VectorStore berisi operasi yang mencakup semua koleksi di penyimpanan vektor, misalnya ListCollectionNames.
Ini juga menyediakan kemampuan untuk mendapatkan VectorStoreCollection<TKey, TRecord> instans.
Microsoft.Extensions.VectorData.VectorStoreCollection<TKey, TRecord>
VectorStoreCollection<TKey, TRecord> mewakili koleksi.
Koleksi ini mungkin atau mungkin tidak ada, dan kelas dasar abstrak menyediakan metode untuk memeriksa apakah koleksi ada, membuatnya, atau menghapusnya.
Kelas dasar abstrak juga menyediakan metode untuk meningkatkan, mendapatkan, dan menghapus rekaman.
Akhirnya, kelas dasar abstrak mewarisi dari IVectorSearchable<TRecord> menyediakan kemampuan pencarian vektor.
Microsoft.Extensions.VectorData.IVectorSearchable<TRecord>
-
SearchAsync<TRecord>dapat digunakan untuk melakukan:- pencarian vektor menerima beberapa input yang dapat divetorisasi oleh generator embedding yang terdaftar atau oleh basis data vektor, jika basis data tersebut mendukungnya.
- Pencarian vektor yang menggunakan vektor sebagai input.
Pengambilan Augmented Generation (RAG) dengan Vector Stores
Abstraksi penyimpanan vektor adalah api tingkat rendah untuk menambahkan dan mengambil data dari penyimpanan vektor.
Semantic Kernel memiliki dukungan bawaan untuk menggunakan salah satu implementasi Vector Store untuk RAG.
Ini dicapai dengan membungkus VectorSearchBase[TKey, TModel] dengan VectorizedSearchMixin[Tmodel], VectorizableTextSearchMixin[TModel] atau VectorTextSearch[TModel] dan mengeksposnya sebagai implementasi Pencarian Teks.
Petunjuk / Saran
Untuk mempelajari selengkapnya tentang cara menggunakan penyimpanan vektor untuk RAG, lihat Cara menggunakan Penyimpanan Vektor dengan Pencarian Teks Kernel Semantik.
Petunjuk / Saran
Untuk mempelajari selengkapnya tentang pencarian teks, lihat Apa itu Pencarian Teks Kernel Semantik?
Abstraksi Penyimpanan Vektor
Antarmuka utama dalam abstraksi Vector Store adalah sebagai berikut.
com.microsoft.semantickernel.data.vectorstorage.VectorStore
VectorStore berisi operasi yang mencakup semua koleksi di penyimpanan vektor, misalnya listCollectionNames.
Ini juga menyediakan kemampuan untuk mendapatkan VectorStoreRecordCollection<Key, Record> instans.
com.microsoft.semantickernel.data.vectorstorage.VectorStoreRecordCollection<Key, Record>
VectorStoreRecordCollection<Key, Record> mewakili koleksi.
Koleksi ini mungkin atau mungkin tidak ada, dan antarmuka menyediakan metode untuk memeriksa apakah koleksi ada, membuatnya, atau menghapusnya.
Antarmuka juga menyediakan metode untuk melakukan upsert, mendapatkan, dan menghapus rekaman.
Akhirnya, antarmuka mewarisi dari VectorizedSearch<Record> dan menyediakan kemampuan pencarian vektor.
com.microsoft.semantickernel.data.vectorsearch.VectorizedSearch<Record>
VectorizedSearch<Record> berisi metode untuk melakukan pencarian vektor.
VectorStoreRecordCollection<Key, Record> mewarisi dari VectorizedSearch<Record> membuatnya dapat digunakan VectorizedSearch<Record> sendiri dalam kasus di mana hanya pencarian yang diperlukan tanpa memerlukan pengelolaan rekam atau koleksi.
com.microsoft.semantickernel.data.vectorsearch.VectorizableTextSearch<Record>
VectorizableTextSearch<Record> berisi metode untuk melakukan pencarian vektor di mana database vektor memiliki kemampuan untuk menghasilkan penyematan secara otomatis. Misalnya, Anda dapat memanggil metode ini dengan string teks dan database akan menghasilkan representasi untuk Anda dan melakukan pencarian pada bidang vektor. Ini tidak didukung oleh semua database vektor dan oleh karena itu hanya diimplementasikan oleh konektor tertentu.
Mulai menggunakan Vector Stores
Mengimpor paket nuget yang diperlukan
Semua antarmuka penyimpanan vektor dan kelas terkait abstraksi tersedia dalam Microsoft.Extensions.VectorData.Abstractions paket nuget.
Setiap implementasi penyimpanan vektor tersedia dalam paket nugetnya sendiri. Untuk daftar implementasi yang diketahui, lihat halaman Konektor Siap Pakai.
Paket abstraksi dapat ditambahkan seperti ini.
dotnet add package Microsoft.Extensions.VectorData.Abstractions
Tentukan model data Anda
Abstraksi Vector Store menggunakan pendekatan model pertama untuk berinteraksi dengan database. Ini berarti bahwa langkah pertama adalah menentukan model data yang memetakan ke skema penyimpanan. Untuk membantu implementasi membuat koleksi rekaman dan memetakan ke skema penyimpanan, model dapat diannotasi untuk menunjukkan fungsi setiap properti.
using Microsoft.Extensions.VectorData;
public class Hotel
{
[VectorStoreKey]
public ulong HotelId { get; set; }
[VectorStoreData(IsIndexed = true)]
public string HotelName { get; set; }
[VectorStoreData(IsFullTextIndexed = true)]
public string Description { get; set; }
[VectorStoreVector(Dimensions: 4, DistanceFunction = DistanceFunction.CosineSimilarity, IndexKind = IndexKind.Hnsw)]
public ReadOnlyMemory<float>? DescriptionEmbedding { get; set; }
[VectorStoreData(IsIndexed = true)]
public string[] Tags { get; set; }
}
from dataclasses import dataclass, field
from typing import Annotated
from semantic_kernel.data.vector import (
DistanceFunction,
IndexKind,
VectorStoreField,
vectorstoremodel,
)
@vectorstoremodel
@dataclass
class Hotel:
hotel_id: Annotated[str, VectorStoreField('key')] = field(default_factory=lambda: str(uuid4()))
hotel_name: Annotated[str, VectorStoreField('data', is_filterable=True)]
description: Annotated[str, VectorStoreField('data', is_full_text_searchable=True)]
description_embedding: Annotated[list[float], VectorStoreField('vector', dimensions=4, distance_function=DistanceFunction.COSINE, index_kind=IndexKind.HNSW)]
tags: Annotated[list[str], VectorStoreField('data', is_filterable=True)]
import com.microsoft.semantickernel.data.vectorstorage.annotations.VectorStoreRecordData;
import com.microsoft.semantickernel.data.vectorstorage.annotations.VectorStoreRecordKey;
import com.microsoft.semantickernel.data.vectorstorage.annotations.VectorStoreRecordVector;
import com.microsoft.semantickernel.data.vectorstorage.definition.DistanceFunction;
import com.microsoft.semantickernel.data.vectorstorage.definition.IndexKind;
import java.util.Collections;
import java.util.List;
public class Hotel {
@VectorStoreRecordKey
private String hotelId;
@VectorStoreRecordData(isFilterable = true)
private String name;
@VectorStoreRecordData(isFullTextSearchable = true)
private String description;
@VectorStoreRecordVector(dimensions = 4, indexKind = IndexKind.HNSW, distanceFunction = DistanceFunction.COSINE_DISTANCE)
private List<Float> descriptionEmbedding;
@VectorStoreRecordData(isFilterable = true)
private List<String> tags;
public Hotel() { }
public Hotel(String hotelId, String name, String description, List<Float> descriptionEmbedding, List<String> tags) {
this.hotelId = hotelId;
this.name = name;
this.description = description;
this.descriptionEmbedding = Collections.unmodifiableList(descriptionEmbedding);
this.tags = Collections.unmodifiableList(tags);
}
public String getHotelId() { return hotelId; }
public String getName() { return name; }
public String getDescription() { return description; }
public List<Float> getDescriptionEmbedding() { return descriptionEmbedding; }
public List<String> getTags() { return tags; }
}
Petunjuk / Saran
Untuk informasi selengkapnya tentang cara membuat anotasi model data Anda, lihat menentukan model data Anda.
Petunjuk / Saran
Sebagai alternatif untuk menganotasi model data Anda, lihat menentukan skema Anda dengan definisi rekaman.
Hubungkan ke database Anda dan pilih koleksi
Setelah Anda menentukan model data, langkah selanjutnya adalah membuat instans VectorStore untuk database pilihan Anda dan memilih kumpulan rekaman.
Dalam contoh ini, kita akan menggunakan Qdrant. Oleh karena itu, Anda harus mengimpor paket NuGet Qdrant.
dotnet add package Microsoft.SemanticKernel.Connectors.Qdrant --prerelease
Jika Anda ingin menjalankan Qdrant secara lokal menggunakan Docker, gunakan perintah berikut untuk memulai kontainer Qdrant dengan pengaturan yang digunakan dalam contoh ini.
docker run -d --name qdrant -p 6333:6333 -p 6334:6334 qdrant/qdrant:latest
Untuk memverifikasi bahwa instans Qdrant Anda aktif dan berjalan dengan benar, kunjungi dasbor Qdrant yang dibangun ke dalam kontainer docker Qdrant: http://localhost:6333/dashboard
Karena database mendukung berbagai jenis kunci dan rekaman, kami memungkinkan Anda menentukan jenis kunci dan rekaman untuk koleksi Anda menggunakan generik.
Dalam kasus kami, jenis rekaman akan menjadi kelas yang Hotel sudah kami tentukan, dan jenis kuncinya adalah ulong, karena HotelId properti adalah ulong dan Qdrant hanya mendukung Guid atau ulong kunci.
using Microsoft.SemanticKernel.Connectors.Qdrant;
using Qdrant.Client;
// Create a Qdrant VectorStore object
var vectorStore = new QdrantVectorStore(new QdrantClient("localhost"), ownsClient: true);
// Choose a collection from the database and specify the type of key and record stored in it via Generic parameters.
var collection = vectorStore.GetCollection<ulong, Hotel>("skhotels");
Karena database mendukung berbagai jenis kunci dan rekaman, kami memungkinkan Anda menentukan jenis kunci dan rekaman untuk koleksi Anda menggunakan generik.
Dalam kasus kami, jenis rekaman akan menjadi kelas yang Hotel sudah kami tentukan, dan jenis kuncinya adalah str, karena HotelId properti adalah str dan Qdrant hanya mendukung str atau int kunci.
from semantic_kernel.connectors.qdrant import QdrantCollection
# Create a collection specify the type of key and record stored in it via Generic parameters.
collection: QdrantCollection[str, Hotel] = QdrantCollection(
record_type=Hotel,
collection_name="skhotels" # this is optional, you can also specify the collection_name in the vectorstoremodel decorator.
)
Karena database mendukung berbagai jenis kunci dan rekaman, kami memungkinkan Anda menentukan jenis kunci dan rekaman untuk koleksi Anda menggunakan generik.
Dalam kasus kami, jenis rekaman akan menjadi kelas yang Hotel sudah kami tentukan, dan jenis kuncinya adalah String, karena hotelId properti adalah String penyimpanan JDBC dan hanya mendukung String kunci.
import com.microsoft.semantickernel.data.jdbc.JDBCVectorStore;
import com.microsoft.semantickernel.data.jdbc.JDBCVectorStoreOptions;
import com.microsoft.semantickernel.data.jdbc.JDBCVectorStoreRecordCollectionOptions;
import com.microsoft.semantickernel.data.jdbc.mysql.MySQLVectorStoreQueryProvider;
import com.mysql.cj.jdbc.MysqlDataSource;
import java.util.List;
public class Main {
public static void main(String[] args) {
// Create a MySQL data source
var dataSource = new MysqlDataSource();
dataSource.setUrl("jdbc:mysql://localhost:3306/sk");
dataSource.setPassword("root");
dataSource.setUser("root");
// Create a JDBC vector store
var vectorStore = JDBCVectorStore.builder()
.withDataSource(dataSource)
.withOptions(
JDBCVectorStoreOptions.builder()
.withQueryProvider(MySQLVectorStoreQueryProvider.builder()
.withDataSource(dataSource)
.build())
.build()
)
.build();
// Get a collection from the vector store
var collection = vectorStore.getCollection("skhotels",
JDBCVectorStoreRecordCollectionOptions.<Hotel>builder()
.withRecordClass(Hotel.class)
.build()
);
}
}
Petunjuk / Saran
Untuk informasi selengkapnya tentang jenis kunci dan bidang apa yang didukung setiap implementasi Vector Store, lihat dokumentasi untuk setiap implementasi.
Membuat koleksi dan menambahkan rekaman
// Placeholder embedding generation method.
async Task<ReadOnlyMemory<float>> GenerateEmbeddingAsync(string textToVectorize)
{
// your logic here
}
// Create the collection if it doesn't exist yet.
await collection.EnsureCollectionExistsAsync();
// Upsert a record.
string descriptionText = "A place where everyone can be happy.";
ulong hotelId = 1;
// Create a record and generate a vector for the description using your chosen embedding generation implementation.
await collection.UpsertAsync(new Hotel
{
HotelId = hotelId,
HotelName = "Hotel Happy",
Description = descriptionText,
DescriptionEmbedding = await GenerateEmbeddingAsync(descriptionText),
Tags = new[] { "luxury", "pool" }
});
// Retrieve the upserted record.
Hotel? retrievedHotel = await collection.GetAsync(hotelId);
Membuat koleksi dan menambahkan rekaman
# Create the collection if it doesn't exist yet.
await collection.ensure_collection_exists()
# Upsert a record.
description = "A place where everyone can be happy."
hotel_id = "1"
await collection.upsert(Hotel(
hotel_id = hotel_id,
hotel_name = "Hotel Happy",
description = description,
description_embedding = await GenerateEmbeddingAsync(description),
tags = ["luxury", "pool"]
))
# Retrieve the upserted record.
retrieved_hotel = await collection.get(hotel_id)
// Create the collection if it doesn't exist yet.
collection.createCollectionAsync().block();
// Upsert a record.
var description = "A place where everyone can be happy";
var hotelId = "1";
var hotel = new Hotel(
hotelId,
"Hotel Happy",
description,
generateEmbeddingsAsync(description).block(),
List.of("luxury", "pool")
);
collection.upsertAsync(hotel, null).block();
// Retrieve the upserted record.
var retrievedHotel = collection.getAsync(hotelId, null).block();
Petunjuk / Saran
Untuk informasi selengkapnya tentang cara membuat penyematan, lihat pembuatan penyematan.
Melakukan pencarian vektor
// Placeholder embedding generation method.
async Task<ReadOnlyMemory<float>> GenerateEmbeddingAsync(string textToVectorize)
{
// your logic here
}
// Generate a vector for your search text, using your chosen embedding generation implementation.
ReadOnlyMemory<float> searchVector = await GenerateEmbeddingAsync("I'm looking for a hotel where customer happiness is the priority.");
// Do the search.
var searchResult = collection.SearchAsync(searchVector, top: 1);
// Inspect the returned hotel.
await foreach (var record in searchResult)
{
Console.WriteLine("Found hotel description: " + record.Record.Description);
Console.WriteLine("Found record score: " + record.Score);
}
Melakukan pencarian vektor
Metode pencarian dapat digunakan untuk mencari rekaman dalam koleksi. Menerima string, yang kemudian di-vektorisasi menggunakan pengaturan pembuatan embedding dalam model atau koleksi, atau menerima vektor yang sudah dihasilkan.
# Do a search.
search_result = await collection.search("I'm looking for a hotel where customer happiness is the priority.", vector_property_name="description_embedding", top=3)
# Inspect the returned hotels.
async for result in search_result.results:
print(f"Found hotel description: {result.record.description}")
Membuat fungsi pencarian
Untuk membuat fungsi pencarian sederhana yang dapat digunakan untuk mencari hotel, Anda dapat menggunakan metode create_search_function pada kumpulan.
Nama dan deskripsi, serta nama dan deskripsi parameter, digunakan untuk menghasilkan tanda tangan fungsi yang dikirim ke LLM saat panggilan fungsi digunakan. Ini berarti bahwa memodifikasi ini dapat berguna agar LLM dapat menghasilkan panggilan fungsi yang benar.
collection.create_search_function(
function_name="hotel_search",
description="A hotel search engine, allows searching for hotels in specific cities, "
"you do not have to specify that you are searching for hotels, for all, use `*`."
)
Ada banyak parameter lain, misalnya seperti inilah versi yang lebih kompleks, perhatikan penyesuaian parameter, dan string_mapper fungsi yang digunakan untuk mengonversi rekaman menjadi string.
from semantic_kernel.function import KernelParameterMetadata
collection.create_search_function(
function_name="hotel_search",
description="A hotel search engine, allows searching for hotels in specific cities, "
"you do not have to specify that you are searching for hotels, for all, use `*`.",
search_type="keyword_hybrid", # default is "vector"
parameters=[
KernelParameterMetadata(
name="query",
description="The terms you want to search for in the hotel database.",
type="str",
is_required=True,
type_object=str,
),
KernelParameterMetadata(
name="tags",
description="The tags you want to search for in the hotel database, use `*` to match all.",
type="str",
type_object=str,
default_value="*",
),
KernelParameterMetadata(
name="top",
description="Number of results to return.",
type="int",
default_value=5,
type_object=int,
),
],
# finally, we specify the `string_mapper` function that is used to convert the record to a string.
# This is used to make sure the relevant information from the record is passed to the LLM.
string_mapper=lambda x: f"Hotel {x.record.hotel_name}: {x.record.description}. Tags: {x.record.tags} (hotel_id: {x.record.hotel_id}) ",
)
Petunjuk / Saran
Untuk sampel lainnya, termasuk contoh end-to-end, lihat repositori Sampel Kernel Semantik.
// Generate a vector for your search text, using your chosen embedding generation implementation.
// Just showing a placeholder method here for brevity.
var searchVector = generateEmbeddingsAsync("I'm looking for a hotel where customer happiness is the priority.").block();
// Do the search.
var searchResult = collection.searchAsync(searchVector, VectorSearchOptions.builder()
.withTop(1).build()
).block();
Hotel record = searchResult.getResults().get(0).getRecord();
System.out.printf("Found hotel description: %s\n", record.getDescription());
Petunjuk / Saran
Untuk informasi selengkapnya tentang cara membuat penyematan, lihat pembuatan penyematan.