Релиз языка программирования Rust 2018 (1.31)

Представлен релиз языка системного программирования Rust 1.31, развиваемого проектом Mozilla. Кроме штатного номера версии выпуск также обозначен как Rust 2018 и преподносится как наиболее важный релиз с момента формирования версии 1.0 в 2015 году. В рамках выпуска проведена работа по консолидации всех улучшений и изменений, подготовленных за последние три года, в виде целостного продукта. Rust 2018 выступит основой для наращивая функциональности в последующие три года, по аналогии с тем, как выпуск Rust 1.0 стал базисом для развития языка в прошедшие три года.

Для разделения несовместимой функциональности введена концепция редакций языка. Редакции с номерами «2015» и «2018» могут использоваться в качестве метки для определения среза состояния языка, затрагивающего только несовместимые изменения (добавлено поле «edition» в секции «[package]» метаданных cargo-пакетов).

Редакция «2015» включает уже стабилизированную к текущему моменту функциональность и все будущие изменения не нарушающие совместимость, а редакция «2018» дополнительно охватывает нарушающие совместимость новшества, предложенные в текущем выпуске 1.31 и утверждённые для реализации в будущем. Кроме самого языка редакции также учитывают состояние инструментария и документации (например, в редакции 2018 в состав введены модули поддержки IDE, rustfmt и Clippy).

Режим «2015» позволяет сохранить полную совместимость с существующими приложениями без внесения нарушающих совместимость изменений. Активировать режим «2018» имеет смысл при желании задействовать в коде будущие возможности языка, такие как ещё не реализованные концепции async/await и «try». Так как данная возможность может потребовать корректировки кода старых программ, написанных до резервирования слов async, await и try, указанные ключевые слова уже внесены в редакцию «2018», несмотря на то, что сама функциональность ещё не добавлена.

Иными словами, в выпуске Rust 1.31 заранее произведена фиксация ключевых слов для ещё не готовых новшеств, нарушающих обратную совместимость, и ожидаемых в последующие три года. При этом грядущие изменения и новшества, не приводящие к нарушению совместимости, по мере своего появления будут доступны для пакетов независимо от выбранной редакции — специфичными для редакции «2018» и не попадающими в редакцию «2015» станут только изменения, нарушающие совместимость.

Основные новшества Rust 1.31:

  • Реализована техника NLL (Non-Lexical Lifetimes), расширившая систему учёта времени жизни заимствованных переменных. Вместо привязки времени жизни на лексическом уровне, NLL осуществляет учёт на уровне набора указателей в графе потока выполнения. Новый подход позволяет увеличить качество проверки заимствования переменных
    (borrow checker) и допустить выполнение некоторых видов корректного кода, использование которого ранее приводило к выводу ошибки. Новое поведение существенно упрощает отладку. Например:

       fn main() {
           let mut x = 5;
           let y = x;
           let z = mut x;
           println!("y: {}", y);
       }
    

    Выполнение данного кода в редакции «2015» приводит к выводу ошибки «cannot borrow ‘x’ as mutable because it is also borrowed as immutable» для всего блока «{}» не детализируя источник проблемы, а начиная с Rust 1.31 при выборе редакции «2018» ошибка будет локализована для выражения ‘println!(«y: {}», y);’, которое вызывает конфликт;

  • Внесены изменения в систему модулей, нацеленные на её упрощение: для большинства случаев убрана необходимость использования «extern crate»; добавлена возможность импорта макросов при помощи выражения «use» вместо атрибута «#[macro_use]»; абсолютные пути начинающиеся с названия пакета (crate) теперь разбираются относительно текущего пакета; возможно сосуществование подкаталогов foo.rs и foo/, при размещении субмодулей в подкаталоге больше не нужен mod.rs. Изменения применимы только в режиме «2018»;
  • Добавлены новые способы упрощённого задания области видимости (lifetime elision) в функциях и заголовках реализаций (impl). Вместо
    «impl‹’a› Reader for BufReader‹’a› {}» теперь можно указывать «impl Reader for BufReader‹’_› {}».

  • Добавлен новый способ определения функций — «const fn», который дополнил уже существующие выражения «fn», «unsafe fn» и «extern fn». Функции, определённые через «const fn», могут вызываться не только как обычные функции, но и использоваться в любом контексте вместо констант, например «const SIX: i32 = foo(5);». Данные функции вычисляются на этапе компиляции, а не в ходе выполнения, поэтому на них накладываются определённые ограничения (допускаются арифметические операции и операции сравнения над целыми числами, запрещены булевые операторы «» и «||», допускается чтение только из констант, можно вызывать только функции, определённые как «const fn» и т.п.);
  • Помимо cargo, rustdoc и rustup в основной состав включены утилиты clippy (linter) и rustfmt (форматирование кода), а также плагины для поддержки интегрированных сред разработки Visual Studio Code, IntelliJ, Atom,
    Sublime Text 3 и Eclipse;

  • Стабилизированы новые атрибуты для инструментов Rust, таких как rustfmt и clippy. Например, «#[allow(clippy::bool_comparison)]» для ограничения применения clippy;
  • В разряд стабильных переведена новая порция API, в том числе From‹NonZeroU8›, From‹Option‹T››, slice::align_to, slice::chunks_exact;
  • В пакетный менеджер Cargo добавлена поддержка параллельной загрузки нескольких пакетов при помощи HTTP/2. За исключением специфичных случаев переведено в разряд необязательных выражение «extern crate».
  • Запущены инициативы по оптимизации Rust для предметно-ориентированных областей. Созданы рабочие группы для развития средства для разработки сетевых сервисов (развивает async/await), создания приложений для командной строки (развивает библиотеки для CLI-интерфейса), поддержки WebAssembly (компиляция и взаимодействие с wasm) и создания решений для встраиваемых устройств (улучшение поддержки ARM).

Напомним, что язык Rust сфокусирован на безопасной работе с памятью, обеспечивает автоматическое управление памятью и предоставляет средства для достижения высокого параллелизма выполнения заданий, при этом обходясь без использования сборщика мусора и runtime. Автоматическое управление памятью в Rust избавляет разработчика от манипулирования указателями и защищает от проблем, возникающих из-за низкоуровневой работы с памятью, таких как обращение к области памяти после её освобождения, разыменование нулевых указателей, выход за границы буфера и т.п. Для распространения библиотек, обеспечения сборки и управления зависимостями проектом развивается пакетный менеджер Cargo, позволяющий получить нужные для программы библиотеки в один клик. Для размещения библиотек поддерживается репозиторий crates.io.

Источник.

Добавить комментарий

Ваш e-mail не будет опубликован. Обязательные поля помечены *

Этот сайт использует Akismet для борьбы со спамом. Узнайте как обрабатываются ваши данные комментариев.