Nota
L'accesso a questa pagina richiede l'autorizzazione. È possibile provare ad accedere o modificare le directory.
L'accesso a questa pagina richiede l'autorizzazione. È possibile provare a modificare le directory.
Importante
Questa funzionalità si trova nella fase sperimentale. Le funzionalità in questa fase sono in fase di sviluppo attivo e possono cambiare significativamente prima di passare alla fase di anteprima o alla versione candidato al rilascio.
Informazioni generali
La selezione di funzioni contestuali è una funzionalità avanzata nel framework dell'agente del kernel semantico che consente agli agenti di selezionare e annunciare in modo dinamico solo le funzioni più rilevanti in base al contesto di conversazione corrente. Anziché esporre tutte le funzioni disponibili al modello di intelligenza artificiale, questa funzionalità usa Retrieval-Augmented Generation (RAG) per filtrare e presentare solo queste funzioni più pertinenti alla richiesta dell'utente.
Questo approccio risolve la sfida della selezione delle funzioni quando si tratta di un numero elevato di funzioni disponibili, in cui i modelli di intelligenza artificiale potrebbero altrimenti faticare a scegliere la funzione appropriata, causando confusione e prestazioni non ottimali.
Funzionamento della selezione di funzioni contestuali
Quando un agente viene configurato con la selezione di funzioni contestuali, sfrutta un archivio vettoriale e un generatore di incorporamento per trovare una corrispondenza semantica con il contesto di conversazione corrente (inclusi i messaggi precedenti e l'input dell'utente) con le descrizioni e i nomi delle funzioni disponibili. Le funzioni più rilevanti, fino al limite specificato, vengono quindi annunciate al modello di intelligenza artificiale per la chiamata.
Questo meccanismo è particolarmente utile per gli agenti che hanno accesso a un ampio set di plug-in o strumenti, assicurando che solo le azioni contestualmente appropriate siano considerate in ogni passaggio.
Esempio di utilizzo
Nell'esempio seguente viene illustrato come configurare un agente per l'uso della selezione di funzioni contestuali. L'agente è configurato per riepilogare le recensioni dei clienti, ma solo le funzioni più rilevanti vengono annunciate al modello di intelligenza artificiale per ogni chiamata. Il GetAvailableFunctions
metodo include intenzionalmente funzioni pertinenti e irrilevanti per evidenziare i vantaggi della selezione contestuale.
// Create an embedding generator for function vectorization
var embeddingGenerator = new AzureOpenAIClient(new Uri("<endpoint>"), new ApiKeyCredential("<api-key>"))
.GetEmbeddingClient("<deployment-name>")
.AsIEmbeddingGenerator();
// Create kernel and register AzureOpenAI chat completion service
var kernel = Kernel.CreateBuilder()
.AddAzureOpenAIChatCompletion("<deployment-name>", "<endpoint>", "<api-key>");
.Build();
// Create a chat completion agent
ChatCompletionAgent agent = new()
{
Name = "ReviewGuru",
Instructions = "You are a friendly assistant that summarizes key points and sentiments from customer reviews. For each response, list available functions.",
Kernel = kernel,
Arguments = new(new PromptExecutionSettings { FunctionChoiceBehavior = FunctionChoiceBehavior.Auto(options: new FunctionChoiceBehaviorOptions { RetainArgumentTypes = true }) })
};
// Create the agent thread and register the contextual function provider
ChatHistoryAgentThread agentThread = new();
agentThread.AIContextProviders.Add(
new ContextualFunctionProvider(
vectorStore: new InMemoryVectorStore(new InMemoryVectorStoreOptions() { EmbeddingGenerator = embeddingGenerator }),
vectorDimensions: 1536,
functions: AvailableFunctions(),
maxNumberOfFunctions: 3, // Only the top 3 relevant functions are advertised
loggerFactory: LoggerFactory
)
);
// Invoke the agent
ChatMessageContent message = await agent.InvokeAsync("Get and summarize customer review.", agentThread).FirstAsync();
Console.WriteLine(message.Content);
// Output
/*
Customer Reviews:
-----------------
1. John D. - ★★★★★
Comment: Great product and fast shipping!
Date: 2023-10-01
Summary:
--------
The reviews indicate high customer satisfaction,
highlighting product quality and shipping speed.
Available functions:
--------------------
- Tools-GetCustomerReviews
- Tools-Summarize
- Tools-CollectSentiments
*/
IReadOnlyList<AIFunction> GetAvailableFunctions()
{
// Only a few functions are directly related to the prompt; the majority are unrelated to demonstrate the benefits of contextual filtering.
return new List<AIFunction>
{
// Relevant functions
AIFunctionFactory.Create(() => "[ { 'reviewer': 'John D.', 'date': '2023-10-01', 'rating': 5, 'comment': 'Great product and fast shipping!' } ]", "GetCustomerReviews"),
AIFunctionFactory.Create((string text) => "Summary generated based on input data: key points include customer satisfaction.", "Summarize"),
AIFunctionFactory.Create((string text) => "The collected sentiment is mostly positive.", "CollectSentiments"),
// Irrelevant functions
AIFunctionFactory.Create(() => "Current weather is sunny.", "GetWeather"),
AIFunctionFactory.Create(() => "Email sent.", "SendEmail"),
AIFunctionFactory.Create(() => "The current stock price is $123.45.", "GetStockPrice"),
AIFunctionFactory.Create(() => "The time is 12:00 PM.", "GetCurrentTime")
};
}
Archivio vettoriale
Il provider è progettato principalmente per lavorare con archivi vettoriali in memoria, che offrono semplicità. Tuttavia, se vengono usati altri tipi di archivi vettoriali, è importante notare che la responsabilità della gestione della sincronizzazione e della coerenza dei dati rientra nell'applicazione host.
La sincronizzazione è necessaria ogni volta che viene modificato l'elenco di funzioni o quando viene modificata l'origine degli incorporamenti delle funzioni. Ad esempio, se un agente ha inizialmente tre funzioni (f1, f2, f3) vettorializzate e archiviate in un archivio vettoriale cloud e successivamente f3 viene rimosso dall'elenco di funzioni dell'agente, l'archivio vettori deve essere aggiornato in modo da riflettere solo le funzioni correnti che l'agente ha (f1 e f2). Se non si aggiorna l'archivio vettoriale, le funzioni irrilevanti vengono restituite come risultati. Analogamente, se i dati usati per la vettorializzazione, ad esempio nomi di funzione, descrizioni e così via, cambiano, l'archivio vettoriale deve essere eliminato e ripopolato con nuovi embedding in base alle informazioni aggiornate.
La gestione della sincronizzazione dei dati in archivi vettoriali esterni o distribuiti può essere complessa e soggetta a errori, soprattutto nelle applicazioni distribuite in cui servizi o istanze diverse possono funzionare in modo indipendente e richiedere l'accesso coerente agli stessi dati. Al contrario, l'uso di un archivio in memoria semplifica questo processo: quando l'elenco di funzioni o l'origine vettorializzazione cambia, l'archivio in memoria può essere facilmente ricreato con il nuovo set di funzioni e i relativi incorporamenti, garantendo coerenza con il minimo sforzo.
Specificando le funzioni
Il provider di funzioni contestuali deve essere fornito con un elenco di funzioni da cui può selezionare quelle più rilevanti in base al contesto corrente. Questa operazione viene eseguita fornendo un elenco di funzioni al functions
parametro del ContextualFunctionProvider
costruttore.
Oltre alle funzioni, è necessario specificare anche il numero massimo di funzioni pertinenti da restituire usando il maxNumberOfFunctions
parametro .
Questo parametro determina il numero di funzioni che il provider considererà quando si selezionano quelle più rilevanti per il contesto corrente.
Il numero specificato non deve essere preciso; funge invece da limite superiore che dipende dallo scenario specifico.
L'impostazione di questo valore troppo basso potrebbe impedire all'agente di accedere a tutte le funzioni necessarie per uno scenario, causando potenzialmente l'errore dello scenario. Al contrario, impostarlo troppo alto può sovraccaricare l'agente con troppe funzioni, che possono causare allucinazioni, un consumo eccessivo di token di input e prestazioni non ottimali.
// Create the provider with a list of functions and a maximum number of functions to return
ContextualFunctionProvider provider = new (
vectorStore: new InMemoryVectorStore(new InMemoryVectorStoreOptions { EmbeddingGenerator = embeddingGenerator }),
vectorDimensions: 1536,
functions: [AIFunctionFactory.Create((string text) => $"Echo: {text}", "Echo"), <other functions>]
maxNumberOfFunctions: 3 // Only the top 3 relevant functions are advertised
);
Opzioni del provider di funzionalità contestuali
Il provider può essere configurato usando la ContextualFunctionProviderOptions
classe , che consente di personalizzare vari aspetti del funzionamento del provider:
// Create options for the contextual function provider
ContextualFunctionProviderOptions options = new ()
{
...
};
// Create the provider with options
ContextualFunctionProvider provider = new (
...
options: options // Pass the options
);
Dimensione del contesto
La dimensione del contesto determina quanti messaggi recenti delle invocazioni precedenti dell'agente vengono inclusi durante la creazione del contesto per una nuova invocazione. Il provider raccoglie tutti i messaggi dalle chiamate precedenti, fino al numero specificato e li antepone ai nuovi messaggi per formare il contesto.
L'uso di messaggi recenti insieme ai nuovi messaggi è particolarmente utile per le attività che richiedono informazioni dai passaggi precedenti di una conversazione. Ad esempio, se un agente effettua il provisioning di una risorsa in una chiamata e la distribuisce nel passaggio successivo, il passaggio di distribuzione può accedere ai dettagli del passaggio di provisioning per ottenere informazioni sulle risorse di cui è stato effettuato il provisioning per la distribuzione.
Il valore predefinito per il numero di messaggi recenti nel contesto è 2, ma può essere configurato in base alle esigenze specificando la NumberOfRecentMessagesInContext
proprietà in ContextualFunctionProviderOptions
:
ContextualFunctionProviderOptions options = new ()
{
NumberOfRecentMessagesInContext = 1 // Only the last message will be included in the context
};
Valore di origine dell'incorporamento del contesto
Per eseguire la selezione di funzioni contestuali, il provider deve vettorizzare il contesto corrente in modo che possa essere confrontato con le funzioni disponibili nell'archivio vettoriale. Per impostazione predefinita, il provider crea l'incorporamento del contesto concatenando tutti i messaggi recenti e nuovi non vuoti in una singola stringa, che viene quindi vettorializzato e usato per cercare le funzioni pertinenti.
In alcuni scenari, è possibile personalizzare questo comportamento per:
- Concentrarsi su tipi di messaggio specifici (ad esempio, solo i messaggi utente)
- Escludere determinate informazioni dal contesto
- Pre-elaborare o riepilogare il contesto prima della vettorializzazione (ad esempio, applicare la riscrittura del prompt)
A tale scopo, è possibile assegnare un delegato personalizzato a ContextEmbeddingValueProvider
. Questo delegato riceve i messaggi recenti e nuovi e restituisce un valore stringa da usare come origine per l'incorporamento del contesto:
ContextualFunctionProviderOptions options = new()
{
ContextEmbeddingValueProvider = async (recentMessages, newMessages, cancellationToken) =>
{
// Example: Only include user messages in the embedding
var allUserMessages = recentMessages.Concat(newMessages)
.Where(m => m.Role == "user")
.Select(m => m.Content)
.Where(content => !string.IsNullOrWhiteSpace(content));
return string.Join("\n", allUserMessages);
}
};
La personalizzazione dell'incorporamento del contesto può migliorare la pertinenza della selezione delle funzioni, in particolare in scenari di agenti complessi o altamente specializzati.
Fonte del valore di incorporamento delle funzioni
Il provider deve vettorizzare ogni funzione disponibile per confrontarla con il contesto e selezionare quelle più rilevanti. Per impostazione predefinita, il provider crea una funzione incorporata concatenando il nome e la descrizione della funzione in una singola stringa, che viene quindi vettorializzata e archiviata nell'archivio vettoriale.
È possibile personalizzare questo comportamento usando la EmbeddingValueProvider
proprietà di ContextualFunctionProviderOptions
. Questa proprietà consente di specificare un callback che riceve la funzione e un token di annullamento e restituisce una stringa da utilizzare come origine per l'incorporamento della funzione. Ciò è utile se si vuole:
- Aggiungere ulteriori metadati di funzione alla fonte di annidamento.
- Pre-elaborare, filtrare o riformattare le informazioni sulla funzione prima della vettorizzazione
ContextualFunctionProviderOptions options = new()
{
EmbeddingValueProvider = async (function, cancellationToken) =>
{
// Example: Use only the function name for embedding
return function.Name;
}
};
La personalizzazione del valore di origine di incorporamento della funzione può migliorare l'accuratezza della selezione della funzione, soprattutto quando le funzioni hanno metadati avanzati e rilevanti per il contesto o quando si vuole concentrare la ricerca su aspetti specifici di ogni funzione.
Passaggi successivi
Esplorare gli esempi di selezione della funzione contestuale
Presto disponibili
Altre informazioni saranno presto disponibili.
Presto disponibili
Altre informazioni saranno presto disponibili.