Personalizar OpenAI con tus datos (1 / 2)

· Características

Cuando preguntamos a OpenAI algo que requiere un contexto específico, por ejemplo:

Who is my father?

OpenAI puede alucinar o responder que no lo sabe.

Para ayudar a OpenAI a responder preguntas específicas, puedes aportar información contextual adicional en el propio prompt.

My father lives in Barcelona and is 50 year's old.

Si volvemos a hacer la misma pregunta a openAI, OpenAI responderá incluyendo el prompt aportado con la información contextual.

Embeddings

OpenAI ofrece una funcionalidad conocida como text embeddings para medir la similitud entre cadenas de texto.

Para cada bloque de texto, capítulo o tema podemos enviar esa información al servicio de Embedding de OpenAI para recibir de vuelta sus datos de embedding (es decir, una lista vectorial de números en coma flotante). Ejemplo de petición:

TsgcHTTP_API_OpenAI._CreateEmbeddings('text-embedding-ada-002', 'My father lives in Barcelona and is 50 year's old.');

Y la respuesta de openAI será algo así:

{
"data": [
{
"embedding": [
-0.006929283495992422,
-0.005336422007530928,
...
-4.547132266452536e-05,
-0.024047505110502243
],
"index": 0,
"object": "embedding"
}
],
}

Una vez recopilados los datos especiales que representan los distintos fragmentos de información que queremos que nuestro chatbot entienda, debemos guardarlos en un lugar seguro (como una base de datos vectorial). Recuerda: solo hacemos este paso una vez. Obtenemos estos datos especiales para la información una sola vez, y solo si la información cambia, los actualizaremos.

Por último, cuando queremos hacer una pregunta al chatbot, primero convertimos la consulta a un vector y con el resultado buscamos en la base de datos creada previamente qué vector es el más similar al de nuestra consulta; una vez encontrado, añadimos el prompt del vector más similar a la pregunta como un embedding.

Ejemplo sencillo

Vamos a crear un ejemplo sencillo para usar embeddings y la librería sgcWebSockets. Primero describiremos a nuestra familia y calcularemos el vector para cada miembro.

oOpenAI := TsgcHTTP_API_OpenAI.Create(nil);
oOpenAI.OpenAIOptions.ApiKey := '<your api key>';
oOpenAI._CreateEmbeddings('text-embedding-ada-002', 'My father lives in Barcelona and is 50 year''s old.');
oOpenAI._CreateEmbeddings('text-embedding-ada-002', 'My mather lives in Berlin and is 47 year''s old.');
oOpenAI._CreateEmbeddings('text-embedding-ada-002', 'My sister lives in Seoul and is 28 year''s old.');

Los resultados anteriores pueden almacenarse en una tabla en la que cada fila es un embedding con el prompt y los datos del vector. 

Prompt Vector
My father lives in Barcelona and is 50 year's old. [0.000742552,-0.0049907574...]
My mather lives in Berlin and is 47 year's old.[-0.027452856,-0.0023051118...]
My sister lives in Seoul and is 28 year's old.[-0.007873567,-0.014787777...]

Ahora que tenemos almacenados nuestros vectores, convertiremos en un vector la pregunta que enviaremos a chatgpt 

oOpenAI := TsgcHTTP_API_OpenAI.Create(nil);
oOpenAI.OpenAIOptions.ApiKey := '<your api key>';
vVectorQuery := oOpenAI._CreateEmbeddings('text-embedding-ada-002', ''Who is my father?''); 

Después buscaremos este vector en la base de datos para detectar cuál es el más similar a la pregunta. A continuación tienes un ejemplo en pseudocódigo:

// search the most similar vector using Cosine Similarity
vMostSimilarVector := 0;
Database.First;
While not Database.EOF do
begin
  vCosineSimilarity := VectorCosineSimilarity(vVectorQuery, Database.FieldByName('Vector'));
  if vConsineSimilarity > vMostSimilarVector then
  begin
    vMostSimilarVector := vCosineSimilarity;
    vContext := Database.FieldByName('Prompt');
  end;
  Database.Next;
end;

Por último, preguntamos a chatgpt añadiendo el embedding encontrado como información contextual. 

vQuestion := 'Who is my father?';
ChatBot := TsgcAIOpenAIChatBot.Create(nil);
ChatBot.OpenAIOptions.ApiKey := '<your api key>';
ShowMessage(ChatBot.ChatAsUser('Answer the question based on the context below.\n\nContext:\n' + vContext + '\nQuestion:' + vQuestion + '\nAnswer:'));