
Книга представляет собой практическое руководство по интеграции искусственного интеллекта в процесс разработки на Python. Рассматривается применение ИИ-ассистентов, включая ChatGPT и аналогичные языковые модели, для повышения эффективности на всех этапах жизненного цикла ПО: от сбора требований и проектирования до написания кода, тестирования, развертывания и мониторинга. На примере сквозного проекта (USB T-Shirt Launcher) и реальных сценариев шаг за шагом показано, как использовать ИИ для автоматизации рутинных задач, генерации чистого и безопасного кода, рефакторинга по принципам SOLID, написания тестов, настройки CI/CD и развертывания в облаке. Изложенная методология универсальна и позволяет применять описанные принципы с любым доступным ИИ-инструментом, превращая его в эффективного помощника для ускорения разработки и повышения качества кода.
ИИ-агент — это программа, которая не просто рассуждает, а сама выполняет действия: ищет информацию в Интернете или локальных файлах, сохраняет данные и многое другое.
Разработка таких агентов — самое перспективное направление в программировании сегодня. А главный инструмент для их создания — библиотека LangChain.
Хотите научиться писать ИИ-агентов на Python с помощью LangChain и построить карьеру в IT? Эта книга для вас.
На трёх простых примерах вы быстро и легко освоите основы ИИ-программирования, научитесь создавать агентов, подключать любые языковые модели, доступные в России, работать с сообщениями, разрабатывать собственные инструменты.
Вы узнаете о продвинутых темах: посредники, управление состоянием и контекстом, прерывания, RAG-агенты, мультиагентные системы, протокол MCP, мультимодальные сообщения. А также реализуете агентов в виде Telegram-ботов, веб-приложений и графических интерфейсов.
Книга содержит множество примеров, листингов и готовых учебных программ, многие из которых пригодятся на практике.

Дронов Владимир Александрович, профессиональный программист, писатель и журналист, работает с компьютерами с 1987 года. Автор более 30 популярных компьютерных книг, в том числе «Django 2.1. Практика создания веб-сайтов на Python», “HTML, JavaScript, PHP и MySQL. Джентльменский набор Web-мастера“, «Python 3. Самое необходимое», «Python 3 и PyQt 5. Разработка приложений», “Laravel. Быстрая разработка современных динамических Web-сайтов на PHP, MySQL, HTML и CSS“, “Angular 4. Быстрая разработка сверхдинамических Web-сайтов на TypeScript и PHP” и книг по продуктам Adobe Flash и Adobe Dreamweaver различных версий. Его статьи публикуются в журналах “Мир ПК” и “ИнтерФейс” (Израиль) и интернет-порталах “IZ City” и “TheVista.ru”.
Книгу “Искусственный интеллект с LangChain. Разработка ИИ-агентов на Python” можно купить в нашем интенет-магазине.
Предисловие 13
ИИ-клиенты и ИИ-агенты. Преимущества ИИ-агентов 13
Почему LangChain? 14
Использованные программные продукты 15
Типографские соглашения 16
ЧАСТЬ I. ВВОДНЫЙ КУРС 19
Глава 1. ИИ-клиент и простой ИИ-агент 21
1.1. Выбор большой языковой модели. GigaChat 21
1.2. Регистрация в личном кабинете GigaChat API и получение ключа авторизации 21
1.3. ИИ-клиент 22
1.3.1. Установка необходимых библиотек 23
1.3.2. Написание ИИ-клиента 23
1.4. Простой ИИ-агент 25
1.4.1. Простой ИИ-агент: создание агента LangChain 25
1.4.2. Простой ИИ-агент: работа с сообщениями 26
1.4.3. Простой ИИ-агент: инструмент 27
1.4.4. Простой ИИ-агент: вводная (системный промпт) 29
1.4.5. Простой ИИ-агент: история сообщений, состояние агента и хранилище состояния 31
1.5. Что еще нужно знать о больших языковых моделях, библиотеке LangChain
и не только? 32
Глава 2. Более сложный ИИ-агент 34
2.1. Более сложный ИИ-агент: начало разработки 34
2.2. Более сложный ИИ-агент: база данных пицц 36
2.3. Более сложный ИИ-агент: инструменты 37
2.3.1. Инструменты, часть 1 37
2.3.2. Инструменты, часть 2 38
2.3.3. Инструменты, часть 3 39
2.4. Более сложный ИИ-агент: вводная 42
2.5. Более сложный ИИ-агент: очистка истории. Посредники 44
2.6. Что еще нужно знать о посредниках, очистке истории и не только? 46
ЧАСТЬ II. БИБЛИОТЕКА LANGCHAIN: ОСНОВНЫЕ ВОЗМОЖНОСТИ 49
Глава 3. Установка библиотеки LangChain. Агенты LangChain 51
3.1. Понятие и назначение агента LangChain 51
3.2. Создание агента LangChain 51
3.3. Задание вводной у агента 53
3.4. Работа агента LangChain 54
3.5. Понятия состояния, общего хранилища и контекста агента LangChain 54
Глава 4. Соединение с языковой моделью 56
4.1. Создание соединения с языковой моделью 56
4.1.1. Использование функции init_chat_model() 56
4.1.1.1. Остальные параметры соединения 58
4.1.2. Использование классов соединений 59
4.2. Поддерживаемые языковые модели и соединение с ними 60
4.2.1. Облачные языковые модели 60
4.2.1.1. «Сбер» GigaChat 60
4.2.1.2. Google Gemini 62
4.2.1.3. YandexGPT 63
4.2.1.4. DeepSeek 65
4.2.2. HuggingFace 66
4.2.3. Ollama 68
Глава 5. Сообщения 70
5.1. Классы сообщений 70
5.1.1. BaseMessage 70
5.1.2. AIMessage 71
5.1.3. ToolMessage 72
5.1.4. Примеры сообщений разных разновидностей 72
5.2. Отправка вопросов и получение ответов: обычный режим 73
5.2.1. Отправка вопроса и получение ответа целиком: обычный режим 74
5.2.1.1. Отправка вопроса с указанием выдать ответ целиком: обычный режим 74
5.2.1.2. Получение ответа целиком: обычный режим 75
5.2.2. Отправка вопроса и получение ответа чанками: обычный режим 76
5.3. Отправка вопросов и получение ответов: конкурентный режим 78
5.4. Отладочный вывод сообщений 79
5.5. Что еще нужно знать о сообщениях? 82
Глава 6. Структурированный вывод 83
6.1. Объявление структуры вывода 83
6.1.1. Типизированные словари 83
6.1.2. Датаклассы 86
6.1.3. Модели Pydantic 86
6.2. Задание структуры вывода 88
6.3. Получение структурированного вывода 88
6.4. Обработка ошибок структурирования вывода 89
6.5. Программа для обработки почтовых адресов 91
6.5.1. Обработчик почтовых адресов: соединение с моделью, вводная и структура адреса 91
6.5.2. Обработчик почтовых адресов: агент и стартовый модуль 92
6.6. Мультиструктурный вывод 95
6.7. Структурированный вывод и языковые модели GigaChat 96
6.8. Что еще нужно знать о структурированном выводе? 97
Глава 7. Инструменты, часть 1 99
7.1. Объявление инструментов 99
7.1.1. Объявление инструментов-функций 99
7.1.2. Объявление инструментов-классов 102
7.2. Указание инструментов при создании агента 103
Глава 8. Инструменты, часть 2 105
8.1. Поиск в Интернете 105
8.1.1. DuckDuckGo 105
8.1.1.1. DuckDuckGo: базовый вывод 106
8.1.1.2. DuckDuckGo: расширенный вывод 106
8.1.1.3. DuckDuckGo: настройки поиска 107
8.1.2. Tavily Search 108
8.2. Поиск на отдельных веб-сайтах 110
8.2.1. Википедия 110
8.2.2. Wikidata 111
8.2.3. Google Books 112
8.3. Работа с базами данных 113
8.3.1. Создание пула соединений с базой данных 114
8.3.2. Создание объекта самой базы данных 115
8.3.3. Создание набора инструментов для работы с базой данных 116
8.3.4. Указание инструментов при создании агента 117
8.3.5. ИИ-программа телефонного справочника 118
8.3.5.1. ИИ-телефонный справочник: соединение с языковой моделью и вводная 118
8.3.5.2. ИИ-телефонный справочник: инструменты для работы
с базой данных 119
8.3.5.3. ИИ-телефонный справочник: агент и остальные модули 119
8.4. Работа с локальными файлами 121
8.4.1. Создание набора инструментов для работы с локальными файлами 121
8.4.2. ИИ-программа для создания заготовок программного кода 122
8.5. Что еще нужно знать об инструментах? 123
Глава 9. Работа с историей сообщений 124
9.1. Доступ к истории сообщений 124
9.1.1. Доступ к истории сообщений в инструментах 124
9.1.2. Доступ к истории сообщений в посредниках 125
9.2. Работа с историей сообщений 126
9.3. Внесение изменений в историю сообщений 127
9.4. Очистка истории сообщений 128
9.4.1. Непосредственное удаление сообщений 128
9.4.2. Обрезка истории 129
9.4.2.1. Обрезка истории: делаем сами 129
9.4.2.2. Обрезка истории: используем функцию trim_messages() 129
9.4.3. Удаление результатов вызова инструментов 131
9.4.4. Подведение итогов 132
ЧАСТЬ III. БИБЛИОТЕКА LANGCHAIN:
РАСШИРЕННЫЕ ВОЗМОЖНОСТИ 135
Глава 10. Посредники, часть 1 137
10.1. Посредники однократного вызова 137
10.1.1. Объявление посредников однократного вызова 137
10.1.2. Результаты, возвращаемые посредниками однократного вызова 139
10.1.2.1. None — не делать ничего 139
10.1.2.2. Сообщения — добавить их в историю 140
10.1.2.3. Команда перехода 140
10.2. Посредники двукратного вызова 141
10.2.1. Объявление посредников двукратного вызова 141
10.2.2. Работа посредников двукратного вызова 143
10.2.3. Классы запроса к языковой модели, вызова инструмента и результата, выданного языковой моделью 143
10.2.3.1. Класс ModelRequest: обращение к языковой модели 143
10.2.3.2. Класс ToolCallRequest: обращение к инструменту 145
10.2.3.3. Класс ModelResponse: результат обращения к языковой модели 145
10.2.4. Результаты, возвращаемые посредниками двукратного вызова 146
10.2.4.1. Изначальный результат обращения к языковой модели
или вызова инструмента 146
10.2.4.2. Результат, сгенерированный посредником 147
10.3. Посредники, создающие вводные 149
10.4. Посредники-классы 150
10.5. Указание посредников при создании агента 152
10.6. Последовательность выполнения посредников 152
Глава 11. Посредники, часть 2 154
11.1. LLMToolSelectorMiddleware: выбор используемых инструментов 154
11.2. ModelCallLimitMiddleware: ограничение количества обращений
к языковой модели 155
11.3. ToolCallLimitMiddleware: ограничение количества вызовов инструмента 156
11.4. ShellToolMiddleware: выполнение команд системной консоли 157
11.5. FilesystemFileSearchMiddleware: поиск файлов 160
11.6. TodoListMiddleware: список запланированных дел 161
11.7. LLMToolEmulator: имитация вызовов инструментов 163
Глава 12. Состояние, контекст агента и общее хранилище 164
12.1. Состояние агента 164
12.1.1. Задание структуры состояния агента 164
12.1.2. Чтение данных из состояния агента 165
12.1.3. Запись данных в состояние агента 166
12.2. Контекст агента 168
12.2.1. Задание структуры контекста агента 168
12.2.2. Указание контекста агента 168
12.2.3. Чтение данных из контекста агента 168
12.3. Общее хранилище 170
12.3.1. Указание общего хранилища 170
12.3.2. Структура общего хранилища 170
12.3.3. Работа с общим хранилищем 171
12.3.3.1. Запись документов 171
12.3.3.2. Чтение документов 171
12.3.3.3. Поиск документов 172
12.3.3.4. Перечисление пространств имен 173
12.3.3.5. Удаление документов 174
12.3.4. Доступ к общему хранилищу 174
Глава 13. Хранилища 177
13.1. Хранилища состояния 177
13.1.1. InMemorySaver: оперативная память 177
13.1.2. SqliteSaver: база данных SQLite 178
13.1.3. MongoDBSaver: база данных MongoDB 179
13.1.4. PostgresSaver: база данных PostgreSQL 180
13.1.5. PyMySQLSaver: база данных MySQL 181
13.2. Общие хранилища 182
13.2.1. InMemoryStore: оперативная память 182
13.2.2. SqliteStore: база данных SQLite 182
13.2.3. MongoDBStore: база данных MongoDB 182
13.2.4. PostgresStore: база данных PostgreSQL 183
13.2.5. PyMySQLStore: база данных MySQL 184
13.3. Что еще нужно знать о хранилищах? 184
Глава 14. Прерывания и преграды 185
14.1. Прерывания 185
14.1.1. HumanInTheLoopMiddleware: встроенный посредник,
выполняющий прерывания 185
14.1.1.1. HumanInTheLoopMiddleware: создание объекта посредника 185
14.1.1.2. HumanInTheLoopMiddleware: реагирование на прерывания 188
14.1.1.2.1. HumanInTheLoopMiddleware: реагирование на прерывания при выдаче ответа целиком 188
14.1.1.2.2. HumanInTheLoopMiddleware: реагирование на прерывания при выдаче ответа чанками 192
14.1.2. Самостоятельное выполнение прерываний и реагирование на них 192
14.1.2.1. Самостоятельное выполнение прерываний 192
14.1.2.2. Реагирование на самостоятельно выполненное прерывание 193
14.2. Преграды 194
14.2.1. Встроенные преграды 194
14.2.1.1. PIIMiddleware: выявление и блокирование конфиденциальных данных 194
14.2.1.2. ShellToolMiddleware: выполнение команд системной консоли — функциональность преграды 196
14.2.2. Написание своих преград 197
Глава 15. Обработка ошибок 199
15.1. Обработка ошибок в инструментах 199
15.1.1. Самостоятельная обработка ошибок 199
15.1.1.1. Обработка ошибок в конкретном инструменте 199
15.1.1.2. Обработка критических ошибок 200
15.1.1.3. Централизованная обработка ошибок в посреднике 200
15.1.2. ToolRetryMiddleware: повторный вызов инструмента в случае ошибки 201
15.2. Обработка ошибок в посредниках 203
15.3. Обработка ошибок в агентах 203
15.4. ModelFallbackMiddleware: переключение на запасную языковую модель 204
Глава 16. Разработка RAG-агентов, часть 1 205
16.1. Первый RAG-агент, использующий программно сформированные документы 205
16.1.1. Первый RAG-агент: документы, содержащие рецепты пицц 206
16.1.2. Первый RAG-агент: сплиттер, эмбеддинг и векторное хранилище 207
16.1.3. Первый RAG-агент: ретривер 208
16.1.4. Первый RAG-агент: вводная и всякие мелочи 210
16.2. Второй RAG-агент, загружающий документ из PDF-файла 211
16.3. Документы LangChain 212
16.3.1. Программное формирование документов 212
16.3.2. Загрузка документов из сторонних файлов. Загрузчики 213
16.3.2.1. Методы загрузчиков, предназначенные для создания документов 213
16.3.2.2. PyPDFLoader: один PDF-файл 214
16.3.2.3. PyPDFDirectoryLoader: все PDF-файлы в указанной папке 214
16.3.2.4. WebBaseLoader: отдельные веб-страницы 215
16.3.2.5. RecursiveUrlLoader: заданная веб-страница и все веб-страницы, на которые она ссылается 216
16.4. Сплиттеры 218
16.4.1. RecursiveCharacterTextSplitter: разбиение с сохранением структуры текста 218
16.4.2. CharacterTextSplitter: быстрое разбиение текста 219
16.4.3. Сплиттеры веб-страниц 220
16.4.3.1. HTMLHeaderTextSplitter: быстрое разбиение по заголовкам 220
16.4.3.2. HTMLSectionSplitter: разбиение по заголовкам на чанки ограниченного размера 221
16.4.3.3. HTMLSemanticPreservingSplitter: разбиение с сохранением структуры содержимого веб-страниц 222
16.5. Что еще нужно знать о разработке RAG-агентов, описанных в этой части темы? 223
Глава 17. Разработка RAG-агентов, часть 2 225
17.1. Эмбеддинги 225
17.1.1. «Сбер» GigaChat Embeddings 225
17.1.2. Google Gemini Embeddings 226
17.1.3. YandexGPT Embeddings 226
17.1.4. Эмбеддинги, доступные на HuggingFace 226
17.1.5. Эмбеддинги, работающие под управлением Ollama 227
17.2. Векторные хранилища 228
17.3.1. Создание векторного хранилища 228
17.3.1.1. InMemoryVectorStore: оперативная память 229
17.3.1.2. Chroma: оперативная память или локальный диск 230
17.3.1.3. PGVector: база данных PostgreSQL 231
17.3.2. Работа с векторным хранилищем 232
17.3. Ретриверы 234
17.4. Инструменты для поиска в векторном хранилище 234
17.5. Что еще нужно знать о разработке RAG-агентов, описанных в этой части темы? 235
Глава 18. Мультиагентные ИИ-программы 236
18.1. Принципы разработки мультиагентных ИИ-программ 236
18.2. Пример: ИИ-программа для работы с файлами и базой данных 237
Глава 19. Глубинные агенты LangChain 241
19.1. ИИ-программа исследователя рынка, основанная на глубинном агенте 242
19.2. Возможности глубинных агентов 244
19.3. Создание глубинных агентов 245
19.4. Описание подчиненных агентов 246
19.4.1. Описание подчиненных агентов в виде словарей 246
19.4.2. Описание подчиненных агентов в виде объектов 247
19.5. Файловые системы глубинных агентов 248
19.5.1. StateBackend: виртуальная, в хранилище состояния 249
19.5.2. StoreBackend: виртуальная, в общем хранилище 250
19.5.3. FilesystemBackend: физическая, в папке с заданным путем 250
19.5.4. CompositeBackend: гибридная 251
19.6. Хранение информации в файлах 252
19.6.1. Заметки для глубинного агента 252
19.6.2. Навыки глубинного агента 254
19.6.3. Сохранение произвольных данных 256
19.7. Прерывания в глубинных агентах 257
Глава 20. Протокол MCP. Доступ к удаленным инструментам 258
20.1. Базовые средства для разработки инструмент-серверов и инструмент-клиентов. MCP-серверы и MCP-клиенты 258
20.1.1. Написание инструмент-серверов 258
20.1.1.1. Создание MCP-сервера 259
20.1.1.2. Создание инструментов 260
20.1.1.3. Активизация MCP-сервера 261
20.1.1.4. Запуск инструмент-сервера 262
20.1.2. Написание инструмент-клиентов 263
20.1.2.1. Создание MCP-клиента 263
20.1.2.2. Получение списка инструментов, предоставляемых
инструмент-серверами 265
20.1.2.3. Особенности работы с агентом в случае использования
удаленных инструментов 265
20.2. Расширенные средства для разработки инструмент-серверов
и инструмент-клиентов 266
20.2.1. Ресурсы 266
20.2.1.1. Создание ресурсов в программе инструмент-сервера 266
20.2.1.2. Загрузка ресурсов в программе инструмент-клиента 267
20.2.2. Перехватчики вызовов 269
20.2.2.1. Объявление перехватчиков вызовов 269
20.2.2.2. Класс MCPToolCallRequest: обращение к удаленному
инструменту 270
20.2.2.3. Результаты, возвращаемые перехватчиками вызовов 272
20.2.2.4. Указание перехватчиков вызовов при создании MCP-клиента 273
20.2.2.5. Последовательность выполнения перехватчиков вызовов 273
20.2.3. Доступ к HTTP-заголовкам в теле инструментов 273
20.2.4. Контекст MCP-сервера и функции обратного вызова MCP-клиента 274
20.2.4.1. Пересылка текстовых сообщений 274
20.2.4.2. Индикация хода процесса 276
20.2.4.3. Запрос у пользователя подтверждения на выполнение операции 278
Глава 21. Мультимодальные сообщения 282
21.1. Работа с мультимодальными сообщениями средствами LangChain 282
21.1.1. Отправка в мультимодальных вопросах содержимого файлов 284
21.2. Мультимодальные сообщения и языковые модели GigaChat 285
21.2.1. Создание мультимодальных вопросов 285
21.2.2. Обработка мультимодальных ответов 287
ЧАСТЬ IV. ОФОРМЛЕНИЕ ИИ-АГЕНТОВ 291
Глава 22. Оформление ИИ-агентов в виде Telegram-ботов 293
22.1. Получение бот-жетона 293
22.2. Простой Telegram-бот: ИИ-приемщик заказов 295
22.2.1. Простой Telegram-приемщик заказов: обработка сообщений 295
22.2.2. Простой Telegram-приемщик заказов: собственно бот 296
22.2.3. Простой Telegram-приемщик заказов: остальной код 299
22.3. Создание Telegram-приложения 300
22.4. Запуск Telegram-приложения 301
22.5. Обработка обновлений разных видов 301
22.5.1. Обработка поступающих команд 301
22.5.1.1. Объявление обработчиков команд 302
22.5.1.2. Update: класс сведений о последнем обновлении 302
22.5.1.3. Message: класс сообщения 303
22.5.1.4. Класс контекста обработчика 304
22.5.1.5. User: класс пользователя Telegram 305
22.5.1.6. Оформление обработчиков команд 306
22.5.1.7. Указание обработчиков у Telegram-приложения 307
22.5.2. Обработка поступающих сообщений 307
22.6. Дополнительные средства для разработки Telegram-ботов 308
22.6.1. Использование экранной клавиатуры 308
22.6.1.1. Создание и вывод экранной клавиатуры 308
22.6.1.2. Реагирование на нажатия кнопок экранной клавиатуры 309
22.6.2. Отправка пользователю изображений 311
22.6.3. Отправка пользователю видео 314
22.7. Что еще нужно знать о разработке Telegram-ботов? 315
Глава 23. Оформление ИИ-агентов в виде веб-приложений 316
23.1. Веб-ИИ-агент, версия 0.1 316
23.1.1. Веб-ИИ-агент, версия 0.1: обработка сообщений 317
23.1.2. Веб-ИИ-агент, версия 0.1: веб-интерфейс 317
23.1.3. Веб-ИИ-агент, версия 0.1: запуск и тестирование 319
23.1.4. Веб-ИИ-агент, версия 0.1: фронтенд 323
23.2. Создание приложения FastAPI 327
23.3. Объявление контроллеров 328
23.3.1. Генерирование и выдача серверных ответов 328
23.3.2. Получение данных от пользователя 329
23.3.2.1. Данные в формате JSON 329
23.3.2.2. Данные в формате Form Data 330
23.3.2.3. GET-параметры 330
23.3.2.4. URL-параметры 331
23.3.2.5. Данные из cookie 331
23.3.3. Создание cookie 332
23.4. Создание маршрутов 332
23.5. Веб-ИИ-агент, версия 1.0 333
23.6. Поддержка протокола Websockets 335
23.6.1. Объявление Websockets-контроллеров 335
23.6.2. WebSocket: класс соединения Websockets 336
23.6.3. Обработка разрыва соединения клиентом 337
23.6.4. Создание Websockets-маршрутов 338
23.7. Веб-ИИ-агент: версия 2.0 338
23.7.1. Веб-ИИ-агент, версия 2.0: бэкенд 338
23.7.1.1. Веб-ИИ-агент, версия 2.0: обработка сообщений 338
23.7.1.2. Веб-ИИ-агент, версия 2.0: веб-приложение 339
23.7.2. Веб-ИИ-агент, версия 2.0: фронтенд 341
23.8. Веб-ИИ-агент, версия 2.1: очистка истории сообщений после разрыва соединения 343
23.9. Что еще нужно знать о разработке веб-ИИ-приложений? 344
Глава 24. Оформление ИИ-агентов в виде графических приложений 346
24.1. Графический ИИ-агент, версия 1.0 346
24.1.1. Графический ИИ-агент, версия 1.0: разработка 346
24.1.2. Графический ИИ-агент, версия 1.0: запуск 349
24.2. Оконные элементы 350
24.2.1. Базовые классы оконных элементов 350
24.2.2. Элементы управления 353
24.2.2.1. Надпись 353
24.2.2.2. Поле ввода 354
24.2.2.3. Флажок 355
24.2.2.4. Группа переключателей 355
24.2.2.5. Раскрывающийся список 356
24.2.2.6. Кнопка 359
24.2.3. Дополнительные оконные элементы 359
24.2.3.1. Графический элемент 359
24.2.3.2. Текст в формате Markdown 360
24.2.4. Контейнеры 361
24.2.4.1. Базовый класс контейнеров 361
24.2.4.2. Колонка 362
24.2.4.3. Строка 363
24.2.4.4. Прокручивающийся перечень 364
24.2.4.5. Сетка 364
24.3. Графический ИИ-агент, версия 1.1 365
24.4. Обработка событий 367
24.5. Вывод оконных элементов в окне 368
24.6. Дополнительные программные инструменты 368
24.6.1. Работа с клиентской областью окна 368
24.6.2. Управление окном 369
24.6.3. Вывод стандартных файловых диалоговых окон 371
24.7. Что еще нужно знать о разработке графических приложений? 373
Заключение 374
Приложение. Описание файлового архива 376
Предметный указатель 377





















