Представьте: через три месяца вы открываете чужой Rust-код и читаете его как книгу.
Arc<Mutex<T>> не вызывает панику. impl Future не пугает. Вы точно знаете, почему компилятор ругается и как это починить за 10 секунд.
Это не фантазия. Это результат 50 уроков, в которых каждая концепция объясняется через код и закрепляется практикой.
Ownership, traits, generics, async, unsafe - всё, что казалось магией, станет рабочим инструментом.А бонусом - портфолио проектов: от CLI-утилит до REST API и WebAssembly.
Вы и так знаете, что Rust - ваш следующий язык. Этот курс просто сделает это реальностью.
Сегодня - 55% процентов от цены, торопись: https://stepik.org/a/269250/
Please open Telegram to view this post
VIEW IN TELEGRAM
👍10❤4🖕4🔥3🥰1🌚1🤗1
MaybeUninit для ручной сборки структур без лишнего drop
Когда значение собирается по частям в unsafe-коде, FFI, парсере или аллокаторе, главная проблема не в самой инициализации. Главная проблема - что делать, если ошибка произошла посередине.
Например, одно поле структуры уже создано, а второе еще нет. В этот момент нельзя дропать всю структуру целиком: для Rust она еще не является полностью готовым объектом.
Правильный подход - явно помнить, какие поля уже инициализированы, и очищать только их. Для этого используют MaybeUninit, ptr::write, drop_in_place и, когда значение уже полностью готово, assume_init_drop.
MaybeUninit нужен не “чтобы обмануть Rust”, а чтобы аккуратно управлять жизненным циклом там, где компилятор уже не может сделать это за тебя.
Для таких случаев есть MaybeUninit:
use std::mem::MaybeUninit;
struct Buffer {
data: Vec<u8>,
meta: String,
}
let mut value = MaybeUninit::<Buffer>::uninit();
unsafe {
let ptr = value.as_mut_ptr();
std::ptr::addr_of_mut!((*ptr).data).write(vec![1, 2, 3]);
// Если дальше случилась ошибка,
// дропаем только уже инициализированное поле
std::ptr::addr_of_mut!((*ptr).data).drop_in_place();
// А всю Buffer не трогаем:
// meta еще не была создана
}
Более удобный вариант для полностью инициализированного MaybeUninit<T>:
let mut value = MaybeUninit::new(String::from("hello"));
unsafe {
value.assume_init_drop();
}
MaybeUninit<T> используют не просто для создания значения “без инициализации”. Он нужен, когда ты сам управляешь моментом, в который память становится настоящим T, и сам отвечаешь за корректный drop.
Если структура собирается по частям, компилятор уже не всегда может понять, какие поля реально созданы. Поэтому unsafe-логику лучше держать внутри маленькой функции или типа, а наружу отдавать обычный safe API. Так риск ошибок остается локальным и проверяемым.
#rust #rustlang #programming #unsafeRust
Please open Telegram to view this post
VIEW IN TELEGRAM
❤10🔥4🥰3🥴2👍1🤗1
Rust-эксперимент, который красиво объясняет, почему `Vec` почти всегда лучший варинт
Автор взял идею из Linux filesystem: inode хранит метаданные и указывает на блоки данных. Потом задал очень опасный, но полезный вопрос: а что если такую же схему перенести в Rust-контейнер?
Так появился
Звучит умно. На практике CPU быстро объясняет, кто здесь главный.
Обычный
Бенчмарки получились ожидаемые, но от этого не менее полезные: в обычных vector-like сценариях
Когда обход сделали не через
Где такая схема может иметь смысл?
В append-heavy системах, где буфер часто растёт, но редко индексируется посередине. Например, логи, event buffers, tracing pipelines, ingestion queues. Там иногда важнее не копировать огромный непрерывный буфер при росте, чем выиграть каждый отдельный доступ.
Ещё один сценарий - chunk-native processing: стриминговая аналитика, batch transforms, сериализация, компрессия, обработка данных кусками. Если ваша логика работает чанками, а не элементами, paged layout уже не выглядит странным.
Если ваша цель - «сделать Vec, только быстрее», inode-style vector в Rust плохая идея.
Если цель - понять, где именно pointer-heavy layout проигрывает contiguous memory, как легко сломать инварианты через
Иногда лучший результат плохой идеи - не победа в бенчмарках, а момент, когда машина наконец показывает, где именно вы ошибались.
https://sot.dev/inode-style-vector-in-rust.html
Автор взял идею из Linux filesystem: inode хранит метаданные и указывает на блоки данных. Потом задал очень опасный, но полезный вопрос: а что если такую же схему перенести в Rust-контейнер?
Так появился
PagedSmallVec: сначала маленький inline-буфер, потом данные раскладываются по фиксированным чанкам, а не лежат одним непрерывным куском памяти.Звучит умно. На практике CPU быстро объясняет, кто здесь главный.
Обычный
Vec почти всегда быстрее, потому что он делает ровно то, что любит процессор: данные лежат подряд, доступ предсказуемый, меньше переходов по указателям, меньше ветвлений, меньше cache misses. У PagedSmallVec каждый доступ после inline-части превращается в математику по чанкам: вычислить индекс чанка, offset, найти нужный блок, достать значение. Для u32 это особенно больно: там сама операция дешёвая, поэтому накладные расходы контейнера видны сразу.Бенчмарки получились ожидаемые, но от этого не менее полезные: в обычных vector-like сценариях
Vec чаще первый, SmallVec обычно второй, а paged-структура чаще третья. На push, pop, random indexing и ordered remove магии не случилось.Когда обход сделали не через
get(i) на каждый элемент, а чанками через for_each_chunk, структура стала выглядеть гораздо разумнее. Потому что её естественная единица работы - не отдельный элемент, а блок. И вот тут появляется главный урок: плохой API может убить даже неплохую идею, если заставляет структуру данных работать против своей природы.Где такая схема может иметь смысл?
В append-heavy системах, где буфер часто растёт, но редко индексируется посередине. Например, логи, event buffers, tracing pipelines, ingestion queues. Там иногда важнее не копировать огромный непрерывный буфер при росте, чем выиграть каждый отдельный доступ.
Ещё один сценарий - chunk-native processing: стриминговая аналитика, batch transforms, сериализация, компрессия, обработка данных кусками. Если ваша логика работает чанками, а не элементами, paged layout уже не выглядит странным.
Если ваша цель - «сделать Vec, только быстрее», inode-style vector в Rust плохая идея.
Если цель - понять, где именно pointer-heavy layout проигрывает contiguous memory, как легко сломать инварианты через
MaybeUninit, почему unsafe-контейнеры требуют железной дисциплины и почему API должен совпадать с layout, то эксперимент отличный.Иногда лучший результат плохой идеи - не победа в бенчмарках, а момент, когда машина наконец показывает, где именно вы ошибались.
https://sot.dev/inode-style-vector-in-rust.html
🔥10❤9👍5🥰1💯1
32 тысячи звёзд на GitHub всего за 10 часов!
Терминал Warp открыли в open-source.
Это одна из самых заметных agentic development environment: терминалом уже пользуются больше 1 млн разработчиков по всему миру. Теперь проект хотят развивать быстрее за счёт комьюнити, внешних контрибьюторов и прозрачной разработки.
open-source-релиз стал возможен при поддержке OpenAI, которые выступили главным спонсором проекта.
Реакция комьюнити мощная: репозиторий за несколько часов собрал уже 30+ тысяч звёзд на GitHub.
И, конечно же, он написан на Rust.
https://github.com/warpdotdev/warp
Терминал Warp открыли в open-source.
Это одна из самых заметных agentic development environment: терминалом уже пользуются больше 1 млн разработчиков по всему миру. Теперь проект хотят развивать быстрее за счёт комьюнити, внешних контрибьюторов и прозрачной разработки.
open-source-релиз стал возможен при поддержке OpenAI, которые выступили главным спонсором проекта.
Реакция комьюнити мощная: репозиторий за несколько часов собрал уже 30+ тысяч звёзд на GitHub.
И, конечно же, он написан на Rust.
https://github.com/warpdotdev/warp
❤28🔥13🥰4🤣4🤗2❤🔥1👍1
🧩 Новый язык программирования для AI-систем
Weft - это язык программирования, написанный на Rust, который упрощает создание AI-приложений, позволяя связывать LLM, людей и API без лишнего "проводки". Он предлагает визуальное представление программ и строгую типизацию, что делает разработку более интуитивной и безопасной.
🚀Основные моменты:
- Первоклассные взаимодействия с людьми через простые узлы.
- Возможность сворачивать группы узлов для упрощения структуры.
- Полная типизация, предотвращающая ошибки на этапе компиляции.
- Устойчивое выполнение программ, сохраняющих состояние после сбоев.
- Встроенные узлы для работы с различными сервисами и API.
📌 GitHub: https://github.com/WeaveMindAI/weft
#rust
Weft - это язык программирования, написанный на Rust, который упрощает создание AI-приложений, позволяя связывать LLM, людей и API без лишнего "проводки". Он предлагает визуальное представление программ и строгую типизацию, что делает разработку более интуитивной и безопасной.
🚀Основные моменты:
- Первоклассные взаимодействия с людьми через простые узлы.
- Возможность сворачивать группы узлов для упрощения структуры.
- Полная типизация, предотвращающая ошибки на этапе компиляции.
- Устойчивое выполнение программ, сохраняющих состояние после сбоев.
- Встроенные узлы для работы с различными сервисами и API.
📌 GitHub: https://github.com/WeaveMindAI/weft
#rust
💊25🤔11🔥5🖕3🥰2❤1🤣1🤗1
Большинство статей про Rust заканчиваются на borrow checker и lifetimes, как будто внутри компилятора живёт только проверяльщик заимствований и злой шрифтовый дизайнер для сообщений об ошибках. На деле там целый зоопарк механизмов, о которых редко пишут даже на конференциях. Я собрал несколько по настоящему любопытных вещей, которые меняют представление о том, как устроен язык изнутри, и подкрепил каждый сюжет кодом, который можно скопировать и проверить самому.
Начнём с того, чего никто не ждёт. Знакомая всем конструкция Option ссылки занимает ровно столько же байт, сколько и обычная ссылка. Это кажется магией: ведь у Option должен быть тег, отличающий Some от None. Никакого тега нет. Компилятор знает, что ссылка в Rust никогда не может быть нулевой, и использует нулевой адрес как представление варианта None. Этот трюк называется niche optimization, и он работает гораздо шире, чем принято думать.
Проверим руками: https://uproger.com/kak-rust-obmanyvaet-proczessor-tajnaya-zhizn-niche-optimizaczii-drop-flags-i-mir/
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥40❤3🥰2⚡1🤗1
🔥 Продвинутый Rust без учебных игрушек
Базу уже прошли? Тогда следующий шаг - production-разработка.
На Stepik идет скидка 60% на продвинутый курс по Rust для тех, кто хочет не просто знать синтаксис, а строить реальные системы.
Внутри: async, unsafe, gRPC, lock-free, observability, Kafka, NATS, axum, tower, CI/CD и канареечный деплой.
Финальный проект - production-ready feed-сервис от архитектуры до релиза.
21 модуль, 84 урока, 400+ проверочных шагов.
Если хотите перейти от маленьких Rust-утилит к коммерческой разработке, сейчас хороший момент зайти: https://stepik.org/a/285608/pay
Базу уже прошли? Тогда следующий шаг - production-разработка.
На Stepik идет скидка 60% на продвинутый курс по Rust для тех, кто хочет не просто знать синтаксис, а строить реальные системы.
Внутри: async, unsafe, gRPC, lock-free, observability, Kafka, NATS, axum, tower, CI/CD и канареечный деплой.
Финальный проект - production-ready feed-сервис от архитектуры до релиза.
21 модуль, 84 урока, 400+ проверочных шагов.
Если хотите перейти от маленьких Rust-утилит к коммерческой разработке, сейчас хороший момент зайти: https://stepik.org/a/285608/pay
❤5👍5🔥4🥰1🤬1🖕1🤗1
🦀 Rust против C в embedded - не на словах, а в реальном тесте.
Исследователи взяли промышленное IoT-железо и запустили на нём две реализации одной и той же функциональности.
Одна команда писала на C.
Другая - на Rust.
Системы работали параллельно несколько месяцев в реальных условиях, а не в синтетическом бенчмарке.
Итог оказался неприятным для старого аргумента «для embedded нужен только C».
Rust не проиграл C ни по памяти, ни по скорости выполнения. Более того, runtime на Ariel OS оказался даже компактнее, чем классический bare-metal стек на C.
Вывод простой: аргумент «C быстрее и легче для прошивок» теперь звучит гораздо слабее.
Rust в embedded - это вполне рабочая альтернатива.
🔗 Подоробности: https://arxiv.org/abs/2604.25679
#Rust #RustLang #EmbeddedSystems #IoT #SystemsProgramming #C
Исследователи взяли промышленное IoT-железо и запустили на нём две реализации одной и той же функциональности.
Одна команда писала на C.
Другая - на Rust.
Системы работали параллельно несколько месяцев в реальных условиях, а не в синтетическом бенчмарке.
Итог оказался неприятным для старого аргумента «для embedded нужен только C».
Rust не проиграл C ни по памяти, ни по скорости выполнения. Более того, runtime на Ariel OS оказался даже компактнее, чем классический bare-metal стек на C.
Вывод простой: аргумент «C быстрее и легче для прошивок» теперь звучит гораздо слабее.
Rust в embedded - это вполне рабочая альтернатива.
🔗 Подоробности: https://arxiv.org/abs/2604.25679
#Rust #RustLang #EmbeddedSystems #IoT #SystemsProgramming #C
🔥49❤9🥰5🤔2🍓2😁1
Как Rust обманывает процессор. Часть 2: niche сквозь крейты, dropck, Pin и провенанс указателей
В первой части мы коснулись niche-оптимизации, drop flags, MIR, Stacked Borrows и async-стейт-машин. Под статьёй справедливо заметили (спасибо, Mingun): про niche рассказано только в самой простой форме —
А что происходит, когда enum живёт в одном крейте, оборачивается в newtype в другом, и оба варианта внешнего enum хранят один и тот же внутренний?
По факту у такого внешнего типа всего четыре состояния - байта должно хватить. Хватит ли?
Ответ короткий: иногда да, иногда нет, и причина не в теории, а в том, как rustc вообще считает layout. С этого и начнём.
https://uproger.com/kak-rust-obmanyvaet-proczessor-chast-2-niche-skvoz-krejty-dropck-pin-i-provenans-ukazatelej/
В первой части мы коснулись niche-оптимизации, drop flags, MIR, Stacked Borrows и async-стейт-машин. Под статьёй справедливо заметили (спасибо, Mingun): про niche рассказано только в самой простой форме —
Option<&T> и NonZeroU8. А что происходит, когда enum живёт в одном крейте, оборачивается в newtype в другом, и оба варианта внешнего enum хранят один и тот же внутренний?
По факту у такого внешнего типа всего четыре состояния - байта должно хватить. Хватит ли?
Ответ короткий: иногда да, иногда нет, и причина не в теории, а в том, как rustc вообще считает layout. С этого и начнём.
https://uproger.com/kak-rust-obmanyvaet-proczessor-chast-2-niche-skvoz-krejty-dropck-pin-i-provenans-ukazatelej/
🔥6❤3👍2🥰1🖕1🤗1
Вопрос простой: если запустить пример в Miri со Stacked Borrows, будет ли там UB?
Но важна не только галочка «да» или «нет».
Если UB есть, нужно объяснить:
- какая именно операция ломает правила;
- почему этот указатель больше нельзя использовать;
- где была нарушена модель заимствований;
- какой доступ инвалидировал предыдущий alias;
- почему компилятор может считать такой код невозможным.
Вот в этом и суть unsafe Rust.
`unsafe` не значит «делай что хочешь». Это значит: компилятор больше не проверяет часть правил за тебя, но правила всё ещё существуют.
Miri полезен именно потому, что заставляет смотреть не на ощущение «ну вроде работает», а на формальную модель памяти.
Код может стабильно проходить локально, не падать в тестах и всё равно быть UB.
А потом оптимизатор сделает вид, что такого состояния программы вообще не могло существовать.
Please open Telegram to view this post
VIEW IN TELEGRAM
👍10🥰3🔥2❤1🖕1🤗1
🦀 Полный roadmap по изучению Rust на русском + бесплатный курс для начинающих + большой список ресурсов.
Rust Roadmap 2026 на русском - пошаговый план изучения Rust для начинающих и продвинутых разработчиков.
Что внутри:
- базовый синтаксис
- ownership, borrowing и lifetimes
- Option, Result, traits и generics
- тестирование и обработка ошибок
- std, smart pointers и многопоточность
- async/await и Tokio
- macros, unsafe и FFI
- web, CLI, embedded, WASM, gamedev и ML
- мини-проекты на каждом этапе
Хорошый Roadmap для тех, кто хочет учить Rust не хаотично, а по нормальному маршруту: от первых программ до production-кода.
Сохраняйте себе и отправляйте коллегам!
https://github.com/Develp10/rust-roadmap-ru/tree/main
Rust Roadmap 2026 на русском - пошаговый план изучения Rust для начинающих и продвинутых разработчиков.
Что внутри:
- базовый синтаксис
- ownership, borrowing и lifetimes
- Option, Result, traits и generics
- тестирование и обработка ошибок
- std, smart pointers и многопоточность
- async/await и Tokio
- macros, unsafe и FFI
- web, CLI, embedded, WASM, gamedev и ML
- мини-проекты на каждом этапе
Хорошый Roadmap для тех, кто хочет учить Rust не хаотично, а по нормальному маршруту: от первых программ до production-кода.
Сохраняйте себе и отправляйте коллегам!
https://github.com/Develp10/rust-roadmap-ru/tree/main
🔥43❤11👍8🥰1🤗1
Если взять случайный крейт с crates.io, поставить на него Miri и подождать минут пять, шанс увидеть красное сообщение про undefined behavior где-то в зависимостях стремится к единице. Чаще всего виноват не автор хитрого unsafe-блока ради скорости, а вполне обычная библиотека, которой пять лет, у которой звёзд на гитхабе больше, чем у твоего пет-проекта строчек кода, и которая всё это время спокойно лежит в продакшене.
Самое неприятное в этой истории то, что компилятор ничего не скажет. Тесты пройдут. Бенчмарки покажут красивые наносекунды. А потом LLVM 19 обновится до LLVM 20, поменяет один проход оптимизации, и твой сервис начнёт ронять прод по понедельникам. Чтобы понять, почему так происходит, придётся залезть в три темы, которые в обычной жизни Rust-разработчика не встречаются: pointer provenance, Stacked Borrows и пришедшую им на смену Tree Borrows.
https://uproger.com/tvoj-kod-na-rust-kompiliruetsya-prohodit-testy-i-yavlyaetsya-ub-ty-prosto-ob-etom-ne-znaesh/
Please open Telegram to view this post
VIEW IN TELEGRAM
👍8🥰3💯3❤1🖕1🤗1
В CUDA появился экспериментальный проект cuda-oxide. Это компилятор, который позволяет писать GPU-кернелы на Rust и получать на выходе PTX для NVIDIA GPU.
Без отдельного DSL. Без прослойки на C++. Без схемы «Rust только управляет, а настоящая работа всё равно в CUDA C++».
Пока это ранняя alpha, так что ждать production-ready инструмента рано. API будет ломаться, баги будут, часть возможностей ещё не закрыта. Но сам ход показательный.
CUDA много лет была территорией C и C++. Rust рядом с ней обычно жил как host-код, биндинги или инфраструктура вокруг вычислений. cuda-oxide пробует другое: дать Rust зайти прямо внутрь GPU-кернелов.
Почему на это стоит обратить внимание:
- можно писать SIMT-код на Rust
- компиляция идёт напрямую в PTX
- не нужно тащить C++-обвязку для каждого критичного участка
- появляется шанс использовать Rust-эргономику в низкоуровневом GPU-коде
- у NVIDIA, похоже, появился серьёзный интерес к Rust-разработчикам
Сейчас это не «убийца CUDA C++» и не повод срочно переписывать ML-инфру.
Но если проект доживёт до стабильной версии, он может сильно упростить жизнь тем, кто пишет HPC, симуляции, ML-runtime и системный GPU-код.
Rust всё дальше уходит из роли «безопасной замены C для серверов» и залезает в зоны, где раньше почти безраздельно сидел C++.
https://github.com/NVlabs/cuda-oxide/releases/tag/v0.1.0
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥50❤17👍5👏3🤗2🥰1