Курс Rust для программистов на C/C++
Обзор курса
- Обзор курса
- Аргументы в пользу Rust (с точки зрения и C, и C++)
- Локальная установка
- Типы, функции, управление потоком выполнения, сопоставление с образцом
- Модули, cargo
- Трейты, обобщения
- Коллекции, обработка ошибок
- Замыкания, управление памятью, времена жизни, умные указатели
- Конкурентность
- Небезопасный Rust, включая Foreign Function Interface (FFI)
no_stdи основы встраиваемого Rust для команд, разрабатывающих прошивки- Примеры из практики: типовые шаблоны перевода реального кода C++ на Rust
- Асинхронный Rust в этом курсе не рассматривается — см. сопутствующий курс по Async Rust, где подробно разобраны футуры, исполнители,
Pin, tokio и промышленные асинхронные шаблоны
Руководство для самостоятельного изучения
Материал подходит как для курса с преподавателем, так и для самостоятельного изучения. Если вы работаете с ним самостоятельно, вот как получить от него максимум пользы:
Рекомендации по темпу:
| Главы | Тема | Примерное время | Контрольная точка |
|---|---|---|---|
| 1–4 | Настройка, типы, управление потоком выполнения | 1 день | Вы можете написать CLI-конвертер температур |
| 5–7 | Структуры данных, владение | 1–2 дня | Вы можете объяснить, почему let s2 = s1 делает s1 недействительной |
| 8–9 | Модули, обработка ошибок | 1 день | Вы можете создать многофайловый проект, который передаёт ошибки дальше с помощью ? |
| 10–12 | Трейты, обобщения, замыкания | 1–2 дня | Вы можете написать обобщённую функцию с ограничениями трейтами |
| 13–14 | Конкурентность, unsafe/FFI | 1 день | Вы можете написать потокобезопасный счётчик с Arc<Mutex<T>> |
| 15–16 | Углублённые темы | В своём темпе | Справочный материал — читайте, когда это актуально |
| 17–19 | Лучшие практики и справочник | В своём темпе | Обращайтесь к нему, когда пишете реальный код |
Как работать с упражнениями:
- В каждой главе есть практические упражнения с указанием сложности: 🟢 Начальный, 🟡 Средний, 🔴 Сложный
- Всегда сначала попробуйте решить упражнение и только потом раскрывайте решение. Борьба с проверкой заимствований — часть обучения, а сообщения компилятора — ваш учитель
- Если вы застряли больше чем на 15 минут, раскройте решение, изучите его, затем закройте и попробуйте снова с нуля
- Rust Playground позволяет запускать код без локальной установки
Если вы упёрлись в стену:
- Внимательно читайте сообщение компилятора: ошибки Rust исключительно полезны
- Перечитайте нужный раздел. Концепции вроде владения (гл. 7) часто становятся понятны при втором прочтении
- Документация стандартной библиотеки Rust отличная: ищите любой тип или метод
- Более глубокие асинхронные шаблоны описаны в сопутствующем курсе Async Rust
Содержание
Часть I — Основы
1. Представление и общий подход
- Знакомство с курсом и общий подход
- Аргументы в пользу Rust
- Как Rust решает эти проблемы?
- Другие ключевые преимущества и возможности Rust
- Краткий справочник: Rust и C/C++
- Почему разработчикам C/C++ нужен Rust
2. Начало работы
- Хватит разговоров: покажите код
- Локальная установка Rust
- Пакеты Rust (крейты)
- Пример: cargo и крейты
3. Встроенные типы и переменные
- Встроенные типы Rust
- Указание типа и присваивание в Rust
- Указание типа и вывод типа в Rust
- Переменные и изменяемость в Rust
4. Управление потоком выполнения
5. Структуры данных и коллекции
- Массивы в Rust
- Кортежи в Rust
- Ссылки в Rust
- Ссылки C++ и ссылки Rust — ключевые различия
- Срезы в Rust
- Константы и статики в Rust
- Строки в Rust: String и &str
- Структуры в Rust
- Тип Vec<T> в Rust
- Тип HashMap в Rust
- Упражнение: Vec и HashMap
6. Сопоставление с образцом и перечисления
7. Владение и управление памятью
- Управление памятью в Rust
- Владение, заимствование и времена жизни в Rust
- Семантика перемещения в Rust
- Clone в Rust
- Трейт Copy в Rust
- Трейт Drop в Rust
- Упражнение: перемещение, копирование и Drop
- Времена жизни и заимствование в Rust
- Аннотации времён жизни в Rust
- Упражнение: хранение срезов с временами жизни
- Углублённый разбор правил элизии времён жизни
- Box<T> в Rust
- Внутренняя изменяемость: Cell<T> и RefCell<T>
- Совместное владение: Rc<T>
- Упражнение: совместное владение и внутренняя изменяемость
8. Модули и крейты
- Крейты и модули в Rust
- Упражнение: модули и функции
- Рабочие пространства и крейты (пакеты)
- Упражнение: использование рабочих пространств и зависимостей пакетов
- Использование крейтов сообщества из crates.io
- Зависимости крейтов и SemVer
- Упражнение: использование крейта rand
- Cargo.toml и Cargo.lock
- Функция cargo test
- Другие возможности Cargo
- Паттерны тестирования
9. Обработка ошибок
- Связываем перечисления с Option и Result
- Тип Option в Rust
- Тип Result в Rust
- Упражнение: реализация функции log() с Option
- Обработка ошибок в Rust
- Упражнение: обработка ошибок
- Лучшие практики обработки ошибок
10. Трейты и обобщения
- Трейты в Rust
- Перегрузка операторов в C++ → трейты std::ops в Rust
- Упражнение: реализация трейта Logger
- Когда использовать enum и dyn Trait
- Упражнение: подумайте, прежде чем переводить
- Обобщения в Rust
- Упражнение: обобщения
- Комбинирование трейтов и обобщений в Rust
- Ограничения трейтов в типах данных
- Упражнение: ограничения трейтов и обобщения
- Паттерн состояний (type state) и обобщения в Rust
- Паттерн-строитель в Rust
11. Расширенные возможности системы типов
- Трейты From и Into в Rust
- Упражнение: From и Into
- Трейт Default в Rust
- Другие преобразования типов в Rust
12. Функциональное программирование
- Замыкания в Rust
- Упражнение: замыкания и захват переменных
- Итераторы в Rust
- Упражнение: итераторы в Rust
- Справочник по инструментам для работы с итераторами
13. Конкурентность
- Конкурентность в Rust
- Почему Rust предотвращает гонки данных: Send и Sync
- Упражнение: подсчёт слов в многопоточном режиме
14. Небезопасный Rust и FFI
- Небезопасный Rust (unsafe)
- Простой пример FFI (функция Rust, вызываемая из C)
- Сложный пример FFI
- Обеспечение корректности unsafe-кода
- Упражнение: написание безопасной обёртки FFI
Часть II — Углублённые темы
15. no_std — Rust для bare metal
- Что такое no_std?
- Когда использовать no_std, а когда std
- Упражнение: кольцевой буфер no_std
- Углублённо о встраиваемых системах
16. Примеры из практики: перевод реального кода C++ на Rust
- Кейс 1: иерархия наследования → диспетчеризация через перечисления
- Кейс 2: дерево на shared_ptr → паттерн арены и индексов
- Кейс 3: коммуникация с фреймворком → заимствование по времени жизни
- Кейс 4: «божественный объект» → компонуемое состояние
- Кейс 5: трейт-объекты — когда они действительно уместны
Часть III — Лучшие практики и справочник
17. Лучшие практики
- Сводка лучших практик Rust
- Избегание избыточного clone()
- Избегание неконтролируемой индексации
- Схлопывание пирамид присваиваний
- Итоговое упражнение: конвейер диагностических событий
- Экосистема логирования и трассировки