Monituj inżynierię na platformie .NET
W tym artykule zapoznasz się z podstawowymi pojęciami dotyczącymi inżynierii monitów. Wiele modeli sztucznej inteligencji jest opartych na monitach, co oznacza, że reagują na tekst wejściowy użytkownika ( monit) z odpowiedzią wygenerowaną przez algorytmy predykcyjne ( ukończenie). Nowsze modele często obsługują również uzupełnianie w formularzu czatu z wiadomościami opartymi na rolach (system, użytkownik, asystent) i historii czatów w celu zachowania konwersacji.
Praca z monitami
Rozważmy ten przykład generowania tekstu, w którym monit to dane wejściowe użytkownika i uzupełnianie to dane wyjściowe modelu:
Monit: "Prezydent, który służył najkrócejszą kadencję, to "
Zakończenie: "Pedro Lascurain".
Ukończenie jest poprawne, ale co zrobić, jeśli aplikacja ma pomóc uczniom historii USA? 45-minutowa kadencja Pedro Lascuraina jest najkrótszym terminem dla każdego prezydenta, ale służył jako prezydent Meksyku. Amerykańscy studenci historii prawdopodobnie szukają "William Henry Harrison". Oczywiście aplikacja może być bardziej przydatna dla jej zamierzonych użytkowników, jeśli dałaś jej jakiś kontekst.
Monituj inżynierię dodaje kontekst do monitu, podając instrukcje, przykłady i wskazówki, aby pomóc modelowi w zapewnieniu lepszych uzupełniania.
Modele obsługujące generowanie tekstu często nie wymagają żadnego określonego formatu, ale należy zorganizować monity, aby było jasne, jaka jest instrukcja i co to jest przykład. Modele, które obsługują aplikacje oparte na czacie, używają trzech ról do organizowania uzupełniania: roli systemu kontrolującej czat, rolę użytkownika reprezentującą dane wejściowe użytkownika i rolę asystenta w zakresie reagowania na użytkowników. Podziel monity na komunikaty dla każdej roli:
- Komunikaty systemowe zapewniają instrukcje dotyczące modelu dotyczące asystenta. Monit może zawierać tylko jeden komunikat systemowy i musi być pierwszym komunikatem.
- Komunikaty użytkownika zawierają monity od użytkownika i wyświetlają przykłady, monity historyczne lub zawierają instrukcje dla asystenta. Przykładowe ukończenie czatu musi zawierać co najmniej jedną wiadomość użytkownika.
- Komunikaty asystenta pokazują przykładowe lub historyczne zakończenia i muszą zawierać odpowiedź na poprzedni komunikat użytkownika. Komunikaty asystenta nie są wymagane, ale jeśli dołączysz jeden, musi być sparowany z komunikatem użytkownika, aby utworzyć przykład.
Instrukcje dotyczące ulepszania ukończenia
Instrukcja to tekst, który informuje model o sposobie reagowania. Instrukcja może być dyrektywą lub imperatywem:
- Dyrektywy mówią modelowi, jak się zachowywać, ale nie są prostymi poleceniami — pomyśl o konfiguracji postaci dla aktora improwizatora: "Pomagasz studentom dowiedzieć się o historii USA, więc mówić o USA, chyba że konkretnie pytają o inne kraje."
- Imperatywami są jednoznaczne polecenia dla modelu do naśladowania. "Przetłumacz na tagalog:"
Dyrektywy są bardziej otwarte i elastyczne niż imperatywne:
- W jednej instrukcji można połączyć kilka dyrektyw.
- Instrukcje zwykle działają lepiej, gdy używasz ich z przykładami. Jednak ze względu na to, że imperatywne są jednoznaczne polecenia, modele nie wymagają przykładów, aby je zrozumieć (choć możesz użyć przykładu, aby pokazać modelowi sposób formatowania odpowiedzi). Ponieważ dyrektywa nie informuje modelu dokładnie o tym, co należy zrobić, każdy przykład może pomóc w lepszej pracy modelu.
- Zwykle lepiej jest podzielić trudną instrukcję na serię kroków, które można wykonać za pomocą sekwencji dyrektyw. Należy również poinformować model, aby wyświetlił wynik każdego kroku, aby można było łatwo wprowadzić szczegółowe korekty. Mimo że możesz podzielić instrukcje na kroki samodzielnie, łatwiej jest po prostu poinformować model, aby to zrobił, i wyświetlić wynik każdego kroku. Takie podejście jest nazywane łańcuchem monitów myślowych.
Kontekst dodawania zawartości podstawowej i pomocniczej
Możesz podać zawartość, aby dodać więcej kontekstu do instrukcji.
Zawartość podstawowa to tekst, który ma przetwarzać model za pomocą instrukcji. Niezależnie od akcji, jaką obejmuje instrukcja, model wykona go na zawartości podstawowej w celu utworzenia ukończenia.
Zawartość pomocnicza to tekst, do którego odwołujesz się w instrukcji, ale który nie jest elementem docelowym instrukcji. Model używa zawartości pomocniczej do ukończenia instrukcji, co oznacza, że obsługa zawartości jest również wyświetlana w uzupełnianiach, zazwyczaj jako pewnego rodzaju struktura (na przykład w nagłówkach lub etykietach kolumn).
Użyj etykiet z zawartością instruktażu, aby ułatwić modelowi ustalenie, jak używać jej z instrukcją. Nie martw się zbytnio o precyzję — etykiety nie muszą dokładnie pasować do instrukcji, ponieważ model obsłuży takie rzeczy jak formularz słów i wielkość liter.
Załóżmy, że do utworzenia listy używasz instrukcji "Podsumuj osiągnięcia prezydenckie w USA". Model może organizować i porządkować go na dowolną liczbę sposobów. Ale co zrobić, jeśli chcesz, aby lista grupować osiągnięcia według określonego zestawu kategorii? Użyj zawartości pomocniczej, aby dodać te informacje do instrukcji.
Dostosuj instrukcję tak, aby grupy modeli według kategorii i dołącz zawartość pomocniczą określającą te kategorie:
prompt = """
Instructions: Summarize US Presidential accomplishments, grouped by category.
Categories: Domestic Policy, US Economy, Foreign Affairs, Space Exploration.
Accomplishments: 'George Washington
- First president of the United States.
- First president to have been a military veteran.
- First president to be elected to a second term in office.
- Received votes from every presidential elector in an election.
- Filled the entire body of the United States federal judges; including the Supreme Court.
- First president to be declared an honorary citizen of a foreign country, and an honorary citizen of France.
John Adams ...' ///Text truncated
""";
Używanie przykładów do kierowania modelem
Przykładem jest tekst pokazujący, jak reagować model, dostarczając przykładowe dane wejściowe użytkownika i dane wyjściowe modelu. Model używa przykładów, aby wywnioskować, co należy uwzględnić w ukończeniach. Przykłady mogą pojawić się przed instrukcjami lub po instrukcji w inżynieryjnym monicie, ale te dwa nie powinny być przeplatane.
Przykład rozpoczyna się od monitu i opcjonalnie może zawierać uzupełnianie. Ukończenie w przykładzie nie musi zawierać odpowiedzi dosłownej — może zawierać tylko sformatowane słowo, pierwszy punktor na liście nieuporządkowanej lub podobny do wskazania, jak każde ukończenie powinno się rozpocząć.
Przykłady są klasyfikowane jako uczenie zero-shot lub uczenie kilku strzałów na podstawie tego, czy zawierają dosłowne ukończenia.
- Przykłady uczenia zero-shot obejmują monit bez dosłownego ukończenia. Takie podejście sprawdza odpowiedzi modelu bez podawania przykładowych danych wyjściowych. Monity zero-shot mogą zawierać uzupełnienia, które zawierają sygnały, takie jak wskazanie, że model powinien wyświetlić uporządkowaną listę, uwzględniając "1". jako ukończenie.
- Przykłady uczenia kilku strzałów obejmują kilka par monitów z dosłownymi ukończeniami. Uczenie kilku strzałów może zmienić zachowanie modelu, dodając do istniejącej wiedzy.
Omówienie wskazówek
Wskazówka to tekst, który przekazuje żądaną strukturę lub format danych wyjściowych. Podobnie jak instrukcja, sygnał nie jest przetwarzany przez model tak, jakby był to dane wejściowe użytkownika. Podobnie jak na przykład, wskazówka pokazuje model, który ma być potrzebny, zamiast mówić mu, co należy zrobić. Możesz dodać dowolną liczbę wskazówek, aby można było wykonać iterację w celu uzyskania żądanego wyniku. Wskazówki są używane z instrukcją lub przykładem i powinny znajdować się na końcu monitu.
Załóżmy, że używasz instrukcji, aby poinformować model o utworzeniu listy osiągnięć prezydenckich według kategorii wraz z zawartością pomocniczą, która informuje model, jakie kategorie mają być używane. Decydujesz, że model ma utworzyć listę zagnieżdżonych ze wszystkimi limitami dla kategorii, z osiągnięciami każdego prezydenta w każdej kategorii wymienionymi w jednej linii, która zaczyna się od ich nazwy, a prezydenci wymienili chronologicznie. Po wykonaniu instrukcji i zawartości pomocniczej można dodać trzy wskazówki, aby pokazać modelowi, jak utworzyć strukturę i sformatować listę:
prompt = """
Instructions: Summarize US Presidential accomplishments, grouped by category.
Categories: Domestic Policy, US Economy, Foreign Affairs, Space Exploration.
Accomplishments: George Washington
First president of the United States.
First president to have been a military veteran.
First president to be elected to a second term in office.
First president to receive votes from every presidential elector in an election.
First president to fill the entire body of the United States federal judges; including the Supreme Court.
First president to be declared an honorary citizen of a foreign country, and an honorary citizen of France.
John Adams ... /// Text truncated
DOMESTIC POLICY
- George Washington:
- John Adams:
""";
- POLITYKA KRAJOWA przedstawia model, który ma rozpocząć każdą grupę z kategorią we wszystkich limitach.
- - George Washington: pokazuje model, aby rozpocząć każdą sekcję z osiągnięciami George'a Washingtona wymienionymi na jednej linii.
- - John Adams: pokazuje model, który powinien zawierać listę pozostałych prezydentów w porządku chronologicznym.
Przykładowy monit przy użyciu platformy .NET
Platforma .NET udostępnia różne narzędzia do monitowania i rozmowy z różnymi modelami sztucznej inteligencji. Użyj jądra semantycznego, aby nawiązać połączenie z wieloma różnymi modelami i usługami sztucznej inteligencji, a także innymi zestawami SDK, takimi jak oficjalna biblioteka platformy .NET OpenAI. Semantyczne jądro zawiera narzędzia do tworzenia monitów z różnymi rolami i obsługi historii czatów, a także wielu innych funkcji.
Rozważmy następujący przykład kodu:
using Microsoft.SemanticKernel;
using Microsoft.SemanticKernel.ChatCompletion;
// Create a kernel with OpenAI chat completion
#pragma warning disable SKEXP0010
Kernel kernel = Kernel.CreateBuilder()
.AddOpenAIChatCompletion(
modelId: "phi3:mini",
endpoint: new Uri("http://localhost:11434"),
apiKey: "")
.Build();
var aiChatService = kernel.GetRequiredService<IChatCompletionService>();
var chatHistory = new ChatHistory();
chatHistory.Add(
new ChatMessageContent(AuthorRole.System, "You are a helpful AI Assistant."));
while (true)
{
// Get user prompt and add to chat history
Console.WriteLine("Your prompt:");
chatHistory.Add(new ChatMessageContent(AuthorRole.User, Console.ReadLine()));
// Stream the AI response and add to chat history
Console.WriteLine("AI Response:");
var response = "";
await foreach (var item in
aiChatService.GetStreamingChatMessageContentsAsync(chatHistory))
{
Console.Write(item.Content);
response += item.Content;
}
chatHistory.Add(new ChatMessageContent(AuthorRole.Assistant, response));
Console.WriteLine();
}
Powyższy kod zawiera przykłady następujących pojęć:
- Tworzy usługę historii czatów w celu monitowania modelu sztucznej inteligencji o ukończenie na podstawie ról autora.
- Konfiguruje sztuczną inteligencję za pomocą komunikatu
AuthorRole.System
. - Akceptuje dane wejściowe użytkownika, aby zezwolić na różne typy monitów w kontekście elementu
AuthorRole.User
. - Asynchronicznie przesyła strumieniowo ukończenie ze sztucznej inteligencji, aby zapewnić dynamiczne środowisko czatu.
Rozszerzanie technik inżynierii monitów
Możesz również zwiększyć możliwości monitów dzięki bardziej zaawansowanym technikom inżynieryjnym, które zostały szczegółowo omówione we własnych artykułach.
- Moduły LLM mają limity danych wejściowych tokenu, które ograniczają ilość tekstu, który można zmieścić w wierszu polecenia. Użyj rozwiązań osadzania i wektorowej bazy danych , aby zmniejszyć liczbę tokenów potrzebnych do reprezentowania danego fragmentu tekstu.
- Maszyny LLM nie są trenowane na danych, chyba że trenujesz je samodzielnie, co może być kosztowne i czasochłonne. Użyj rozszerzonej generacji pobierania (RAG), aby udostępnić dane maszynie LLM bez ich trenowania.