Оглавление
Структурированное формирование выходных данных
Structured Output Prompting (структурированное формирование выходных данных) – это техника, при которой мы «просим» ИИ выдавать результаты в заранее определенном формате, например, JSON, XML или YAML.
Вместо расплывчатых ответов мы получаем четкую структуру данных. Это достигается путем добавления в промпт (запрос к ИИ) инструкций о желаемом формате вывода. Например, вместо просьбы «извлеки информацию о книге» мы говорим: «извлеки название, автора и год издания книги и представь это в формате JSON».
Извлеки название, автора и год издания книги "Мастер и Маргарита" и представь это в формате JSON.
В результате мы получим:
{
"title": "Мастер и Маргарита",
"author": "Михаил Булгаков",
"year": 1967
}
Основное преимущество – гарантированная валидность данных. Если мы указали схему JSON, то ИИ выдаст результат, соответствующий этой схеме. Это упрощает автоматическую обработку и анализ данных. Другое важное преимущество – легкость парсинга (разбора) данных. JSON, XML и YAML легко читаются машинами, что позволяет быстро интегрировать результаты работы ИИ в существующие системы.
Модель находит применение в самых разных областях — в электронной коммерции для автоматического извлечения характеристик товаров, в финансах для анализа новостей и отчетов, в медицине для обработки медицинских записей. Технологии активно используются в связке с retrieval-augmented generation (RAG) для создания сложных автоматизированных рабочих процессов.
Основные форматы: JSON, XML и YAML
JSON: Машинно-читаемая точность
JSON (JavaScript Object Notation) – это текстовый формат обмена данными, основанный на парах «ключ-значение». Его лаконичность и простота делают его идеальным для машинной обработки. JSON особенно хорошо подходит для автоматизации задач, где важна скорость и точность. Например, OpenAI function-calling использует JSON для определения структуры функций, которые может вызывать LLM. Интеграция с LangChain также упрощается благодаря JSON.
{
"product_name": "Смартфон XYZ",
"price": 499.99,
"features": ["5G", "AMOLED display", "128GB storage"]
}
Пример выше показывает, как можно представить информацию о продукте в JSON.
XML: Человеко-читаемая структура
XML (eXtensible Markup Language) – это язык разметки, который использует теги для определения элементов данных. В отличие от JSON, XML более читаем для человека благодаря своей структуре, напоминающей HTML. XML часто используется для структурирования инструкций и конфигурационных файлов. Claude, например, может быть оптимизирован для работы с XML, где теги , и четко определяют роли различных частей данных.
Смартфон XYZ
499.99
5G
AMOLED display
128GB storage
YAML: Простота и гибкость
YAML (YAML Ain’t Markup Language) – это формат сериализации данных, ориентированный на удобочитаемость. Он использует отступы для обозначения структуры, что делает его более компактным и понятным, чем XML. YAML поддерживает многострочные стили, что полезно для длинных текстовых блоков. Для валидации YAML-файлов может использоваться PyYAML.
product_name: Смартфон XYZ
price: 499.99
features:
- 5G
- AMOLED display
- 128GB storage
description: |
Этот смартфон обладает отличными характеристиками
и идеально подходит для повседневного использования.
Руководство по сравнению и выбору форматов
Выбор формата зависит от конкретной задачи:
- JSON идеально подходит для автоматизации и обмена данными между системами
- XML хорош для структурирования инструкций и конфигурационных файлов, где важна читаемость
- YAML – отличный выбор для конфигурационных файлов и данных, которые должны быть легко читаемы и редактируемы человеком
GPT-4o, современные модели Claude (например, Sonnet 4.5) и Gemini поддерживают различные структурированные форматы. Gemini нативно поддерживает JSON и перечисления для структурированного вывода, в то время как Claude активно использует XML-теги для структурирования промптов и вывода.
Выбор часто сводится к личным предпочтениям и требованиям проекта. Если нужна максимальная скорость обработки – выбирайте JSON. Если важна читаемость и возможность ручного редактирования – YAML или XML.
Методы структурированного промптинга
Промптинг на основе инструкций
Самый простой способ получить структурированный вывод — четко указать желаемый формат в инструкции. Важно не просто попросить ИИ извлечь информацию, а явно указать, как именно она должна быть представлена. Например, вместо «Опиши этот товар» лучше написать: «Извлеки название товара, цену и основные характеристики и представь это в формате JSON». Чем детальнее инструкция, тем выше вероятность получить желаемый результат.
Пример:
Извлеки информацию о фильме "Начало" и представь ее в формате JSON, включающем название, год выпуска, режиссера и список актеров.
Такой промпт даст более предсказуемый и структурированный результат, чем просто «Расскажи о фильме Начало». Важно помнить, что даже с четкими инструкциями ИИ может ошибаться, поэтому всегда полезно проверять результат на соответствие ожидаемой структуре. Лучше сразу предусмотреть обработку ошибок, чем потом вручную исправлять неверные данные.
Обучение на нескольких примерах
Few-shot learning (обучение на нескольких примерах) – это метод, при котором в промпт включаются примеры желаемого вывода. Это помогает ИИ лучше понять, какой именно формат требуется. Предоставление нескольких примеров с разными входными данными и соответствующими структурированными выводами значительно повышает точность.
Пример:
Вот несколько примеров извлечения информации о книгах в формате JSON:
Вход: "Книга '1984' написана Джорджем Оруэллом в 1949 году."
Вывод:
{
"title": "1984",
"author": "Джордж Оруэлл",
"year": 1949
}
Вход: "Автором 'Мастера и Маргариты' является Михаил Булгаков, книга написана в 1967 году."
Вывод:
{
"title": "Мастер и Маргарита",
"author": "Михаил Булгаков",
"year": 1967
}
Теперь извлеки информацию о книге "Гарри Поттер и философский камень", написанной Джоан Роулинг в 1997 году, и представь ее в формате JSON.
Чем больше примеров, тем лучше ИИ понимает закономерности и выдает более точные результаты. Однако, стоит помнить о лимите контекста – слишком большое количество примеров может привести к обрезанию промпта.
Рассуждение по цепочке
Chain-of-thought (цепочка рассуждений) – это метод, при котором ИИ сначала «думает» вслух, поэтапно рассуждая о задаче, а затем выдает структурированный результат. Это особенно полезно для сложных задач, требующих логического мышления.
Пример:
Сначала поэтапно рассуждай, а затем извлеки информацию о следующем предложении и представь ее в формате JSON: "Температура воздуха в Москве сегодня 25 градусов Цельсия, ветер северный, 5 м/с."
Рассуждение:
1. Нужно извлечь информацию о температуре, ветре и скорости ветра.
2. Температура указана в градусах Цельсия.
3. Направление ветра - северный.
4. Скорость ветра - 5 м/с.
Вывод:
{
"temperature": "25 градусов Цельсия",
"wind_direction": "северный",
"wind_speed": "5 м/с"
}
Этот метод помогает ИИ лучше понять задачу и избежать ошибок.
Промптинг на основе ролей и вызова функций
Role-based prompting (назначение роли) – это метод, при котором ИИ «играет» определенную роль, например, «эксперта по анализу данных». Function-call prompting (вызов функций) – это метод, при котором ИИ вызывает заранее определенные функции для получения структурированных данных.
Пример (Role-Based):
Представь, что ты эксперт по анализу данных. Извлеки из следующего текста информацию о продажах и представь ее в формате JSON: "В первом квартале продажи выросли на 10%, во втором - на 15%, в третьем - на 5%."
Пример (Function-Call):
Предположим, у нас есть функция extract_sales_data(text)
, которая извлекает данные о продажах из текста и возвращает их в формате JSON.
Вызови функцию extract_sales_data для следующего текста: "В первом квартале продажи выросли на 10%, во втором - на 15%, в третьем - на 5%."
Промптинг на базе вызова функций требует предварительной настройки функций, но обеспечивает максимальный контроль над структурой вывода. OpenAI GPT-4 (и GPT-4o) и Claude активно используют этот подход.
Лучшие практики для надежных результатов
Четкость и конкретика
Четкость и конкретика – залог успеха. Избегайте двусмысленности в запросах. Укажите, какую именно информацию вы хотите получить и в каком формате.
Например, вместо «Извлеки информацию о пользователе» напишите: «Извлеки имя, email и дату регистрации пользователя и верни это как JSON объект». Используйте фразы, которые явно указывают на желаемый формат: «Return as JSON object», «Use YAML format». Чем точнее запрос, тем меньше вероятность ошибок.
Контекст и ограничения
Предоставление контекста помогает ИИ лучше понять задачу. Укажите, откуда берутся данные, какие ограничения существуют (например, лимит токенов). Ограничения помогают избежать «разрастания» ответа и фокусируют ИИ на главном.
Например, можно указать: «Ответ должен быть не более 200 токенов». Важно также указать схему данных, которой должен соответствовать вывод. Это можно сделать, например, с помощью JSON Schema.
Итеративное улучшение
Итеративное улучшение – важная часть процесса. Начните с простого запроса, оцените результат и постепенно усложняйте запрос, добавляя детали и уточнения. Используйте стратегии повторных попыток, если первая попытка не удалась. Например, в PocketFlow Node можно указать max_retries=3
при определении узла, чтобы автоматически повторить запрос три раза в случае ошибки. Не бойтесь экспериментировать с разными формулировками и подходами.
Распространенные ошибки и решения
Распространенные ошибки – ошибки форматирования и галлюцинации. Чтобы избежать ошибок форматирования, используйте валидацию с помощью Pydantic или Zod. Эти библиотеки позволяют проверить, соответствует ли вывод заданной схеме.
Для борьбы с галлюцинациями используйте разложение промпта на более мелкие части. Вместо одного сложного запроса разбейте задачу на несколько простых. «Explain step-by-step» – магическая фраза, которая помогает ИИ более осознанно подходить к задаче и уменьшает вероятность галлюцинаций.
Пример:
Для валидации JSON ответа можно использовать следующий код на Python с Pydantic v2+:
from pydantic import BaseModel, field_validator
import json
class User(BaseModel):
name: str
email: str
registration_date: str
@field_validator('email')
@classmethod
def email_must_contain_at_symbol(cls, email):
if '@' not in email:
raise ValueError('Invalid email format')
return email
json_data = '{"name": "John Doe", "email": "john.doeexample.com", "registration_date": "2024-01-01"}'
try:
user = User.model_validate_json(json_data)
print("Valid JSON")
except Exception as e:
print(f"Invalid JSON: {e}")
Этот код проверяет, соответствует ли JSON объект схеме User
и содержит ли email символ @
.
Практическое руководство по реализации
Примеры извлечения данных
Структурированное выходное подсказывание значительно упрощает извлечение данных. Рассмотрим пример извлечения информации о событии календаря с использованием Python и библиотеки openai в связке с Pydantic для валидации:
from openai import OpenAI
from pydantic import BaseModel, Field
from datetime import datetime
class CalendarEvent(BaseModel):
title: str = Field(description="Название события")
start_time: datetime = Field(description="Время начала события")
end_time: datetime = Field(description="Время окончания события")
location: str = Field(description="Место проведения события")
client = OpenAI()
def extract_event_info(text: str) -> CalendarEvent:
response = client.responses.parse(
model="gpt-4o-2024-08-06", # Или более поздняя версия gpt-4o, поддерживающая Structured Outputs
input=[{"role": "user", "content": f"Извлеки информацию о событии из текста: {text} и представь в формате JSON, соответствующем схеме CalendarEvent."}],
text_format=CalendarEvent
)
return response.output_parsed
event_text = "Встреча с командой завтра в 10:00 в офисе, заканчиваем в 12:00."
event = extract_event_info(event_text)
print(event)
Этот код использует новый метод client.responses.parse
для автоматической валидации и приведения ответа к нужному типу с помощью Pydantic. Если LLM выдаст невалидный JSON, Pydantic выбросит исключение.
Суммирование и анализ
Структурированное выходное подсказывание также полезно для задач суммирования и анализа. Например, можно извлечь ключевые темы и тональность текста и представить их в JSON:
from openai import OpenAI
from pydantic import BaseModel, Field
class SentimentAnalysis(BaseModel):
summary: str = Field(description="Краткое содержание текста")
sentiment: str = Field(description="Тональность текста (положительная, отрицательная, нейтральная)")
key_topics: list[str] = Field(description="Список ключевых тем")
client = OpenAI()
def analyze_sentiment(text: str) -> SentimentAnalysis:
response = client.responses.parse(
model="gpt-4o-2024-08-06", # Или более поздняя версия gpt-4o, поддерживающая Structured Outputs
input=[{"role": "user", "content": f"Проанализируй текст: {text} и представь результат в формате JSON, соответствующем схеме SentimentAnalysis."}],
text_format=SentimentAnalysis
)
return response.output_parsed
text = "Сегодня был отличный день! Погода прекрасная, и я успел сделать много дел."
analysis = analyze_sentiment(text)
print(analysis)
Этот код также использует client.responses.parse
для получения структурированного вывода.
Интеграция с API и инструментами
Структурированное выходное подсказывание упрощает интеграцию с внешними API и инструментами. Например, можно использовать LangChain для создания цепочек, которые автоматически извлекают данные и передают их в другие сервисы.
Обработка ошибок и валидация
Валидация – критически важный шаг. Используйте Pydantic (Python) или Zod (JavaScript) для проверки соответствия структуры данных.
Пример (JavaScript с Zod):
import { z } from "zod";
const UserSchema = z.object({
name: z.string(),
email: z.string().email(),
age: z.number().min(18),
});
const userData = { name: "John Doe", email: "invalid-email", age: 17 };
try {
const validatedData = UserSchema.parse(userData);
console.log("Valid data:", validatedData);
} catch (error) {
console.error("Validation error:", error.errors);
}
Всегда предусматривайте обработку ошибок. Если LLM выдает невалидный JSON, повторите запрос с более четкими инструкциями или используйте резервный механизм.
Часто задаваемые вопросы (FAQ)
Какой формат выбрать: JSON, XML или YAML?
Выбор формата зависит от ваших задач.
- JSON идеально подходит для машинной обработки и скорости, например, при работе с API.
- XML подойдет, если важна читаемость человеком и структурирование данных, как в конфигурационных файлах, и особенно хорошо работает с моделями, такими как Claude, которые были обучены на данных с XML-структурой.
- YAML – золотая середина, сочетающая удобочитаемость и гибкость, удобен для конфигураций и хранения данных.
Для простоты начните с YAML, а затем переходите к JSON для оптимизации.
Как избежать ошибок форматирования?
Используйте валидацию — в Python с Pydantic или в JavaScript с Zod. Эти библиотеки проверяют, соответствует ли вывод заданной схеме. Например, Pydantic поможет убедиться, что все обязательные поля в JSON присутствуют и имеют правильный тип. Лучше проверить сразу, чем потом искать ошибку в коде.
Какую модель LLM лучше использовать для структурированного вывода?
GPT-4o от OpenAI отлично справляется с JSON, обеспечивая высокую точность и скорость, особенно с функцией Structured Outputs. Claude от Anthropic хорошо работает с XML, особенно если нужно структурировать большие объемы данных, благодаря своей архитектуре обучения. Gemini от Google также поддерживает структурированный вывод в JSON и enum-значениях, включая JSON Schema. Попробуйте разные модели и сравните результаты на своих данных.
Как интегрировать структурированный вывод в существующие приложения?
Используйте библиотеки для парсинга (разбора) данных. В Python это json
, xml.etree.ElementTree
и PyYAML
. В JavaScript – встроенный JSON.parse()
и библиотеки вроде js-yaml
и xml2js
. Убедитесь, что ваш код корректно обрабатывает возможные ошибки парсинга.
Что делать, если модель отказывается выдавать структурированный вывод?
Уточните запрос! Добавьте примеры желаемого формата (few-shot learning). Используйте chain-of-thought reasoning, чтобы модель сначала «думала вслух», а затем выдавала результат. Если ничего не помогает, попробуйте другую модель или измените подход к формированию запроса.
Оставить комментарий