LINUX.ORG.RU

Rust 1.34

 ,


2

11
  • cargo теперь умеет в сторонние репозитории

  • оператор ? теперь может использоваться в доктестах

  • стабилизированы трейты TryFrom и TryInto

  • стабилизированы типы AtomicU8AtomicU64 и AtomicI8AtomicI64 в дополнение к имевшимся ранее Atomic{Bool,Ptr,USize,ISize}

  • стабилизированы типы NonZeroI8NonZeroI128 и NonZeroISize в дополнение к имевшимся ранее беззнаковым аналогам

https://blog.rust-lang.org/2019/04/11/Rust-1.34.0.html

Ответ на: комментарий от anonymous

Это не странность, если бы вы почитали выхлоп компилятора, то вы бы поняли, что а мувится в первом цикле

let a = vec![1, 2, 3, 4, 5];
  |         - move occurs because `a` has type `std::vec::Vec<i32>`, which does not implement the `Copy` trait
3 | 
4 |     for i in a {
  |              - value moved here
...
7 |     for i in a {
  |              ^ value used here after move

snake266 ()
Ответ на: комментарий от snake266

Ну так толка от этой фичи никакого. А пример демонстрирует ограничения.

Покажите, что такого скажет раст, чего не скажет статический анализатор или там санитайзер для C++?

anonymous ()
Ответ на: комментарий от anonymous

У вас в первом цикле вектор a преобразуется во владеющий итератор. Владеющий итератор забирает данные у вектора, а сам вектор «уничтожается». Во втором цикле вы пытаетесь повторно использовать a, которого больше нет. За это вы получаете по рукам.

Для того, чтобы это «заработало», необходимо использовать заимствующий итератор, который будет одалживать элементы у вектора, но не забирать. Пример уже дали выше.

anonymous ()
Ответ на: комментарий от anonymous

Я не спрашивал, почему так работает и как сделать, чтоб заработало.

Я всего-лишь сказал, что этого примера уже достаточно, чтобы задуматься об адекватности языка и его подходов.

anonymous ()
Ответ на: комментарий от anonymous
#[derive(Debug)]
struct A(i32);

impl Drop for A {
    fn drop(&mut self) {
        println!("dropped: {:?}", self.0)
    }
}

fn main() {
    let a = vec![A(1), A(2), A(3)];
    for i in a {
        println!("{:?}", i);
    }
}
A(1)
dropped: 1
A(2)
dropped: 2
A(3)
dropped: 3

вот для этого покажи аналог на С++

MyTrooName ★★★★★ ()
Ответ на: комментарий от mersinvald

Анон выше неосилил почитать доку языка, а виноват раст, лол

Анон выше специально написал, что ему понятно, что там и как.

Просто это не меняет ничего в плане адекватности языка.

anonymous ()
Ответ на: комментарий от MyTrooName

вот для этого покажи аналог на С++

Нормальные языки не занимаются неявным уничтожением элементов векторов при простом проходе по нему.

anonymous ()
Ответ на: комментарий от anonymous

Иные подходы в общем случае могут дать как положительный, так и отрицательный эффект.

Согласен.

Так почему же он будет положительным?

Если мы говорим про Rust, то язык вынуждает проектировать на более «низком» уровне и применять обобщения. Но в результате получаются системы, хорошо приспособленные к повторному использованию и расширению.

anonymous ()
Ответ на: комментарий от anonymous

Если мы говорим про Rust, то язык вынуждает проектировать на более «низком» уровне и применять обобщения. Но в результате получаются системы, хорошо приспособленные к повторному использованию и расширению.

Аминь.

anonymous ()
Ответ на: комментарий от anonymous

Ну и нахрена?

ты спрашиваешь, нахрена освобождать объект, как только он больше не нужен? или буквально, нахрена нужна неявная move-семантика?

MyTrooName ★★★★★ ()
Последнее исправление: MyTrooName (всего исправлений: 1)
Ответ на: комментарий от MyTrooName

с того, что там проход с поглощением. был бы нужен - была бы ссылка &a.

Мда. Обсуждаем адекватность языка, а он рассказывает, как он работает.

Ок, что будет, если мы заменим vec![1,2,3,4,5] на &[1, 2, 3, 4, 5]?

anonymous ()
Ответ на: комментарий от anonymous

Обсуждаем адекватность языка

«rust неадекватен» - это не обсуждение.

Ок, что будет, если мы заменим vec1,2,3,4,5 на &[1, 2, 3, 4, 5]?

play.rust-lang.org в помощь. какой у тебя ко мне вопрос?

в твоем примере ничего не изменится - у тебя int-ы. уберешь Copy и добавишь отладочный вывод в деструктор - увидишь разницу.

MyTrooName ★★★★★ ()
Последнее исправление: MyTrooName (всего исправлений: 1)
Ответ на: комментарий от anonymous

Нет, он даст сделать вторую итерацию

второй цикл, ты имеешь ввиду. да, даст. я забыл, что у тебя там два цикла.

тебя что-то в таком поведении смущает?

если ты &a вынесешь из for-ов в определение переменной, мало что меняется. ну будет у тебя одна немутабельная ссылка на объект, а не две. и что?

или ты хочешь поглотить объект, который приходит к тебе по ссылке?

MyTrooName ★★★★★ ()
Последнее исправление: MyTrooName (всего исправлений: 2)
Ответ на: комментарий от anonymous

Но раз вам нравится, то кушайте на здоровье=)

абсолютно

Неадекватность

я это понимаю как «не так как я привык»

покажи аналог с поглощением на плюсах, сравним.

MyTrooName ★★★★★ ()
Последнее исправление: MyTrooName (всего исправлений: 1)
Ответ на: комментарий от MyTrooName

я это понимаю как «не так как я привык»

А зачем привыкать к чему-то маргинальному? Хоть один язык еще занимается подобным?

покажи аналог с поглощением на плюсах, сравним.

Зачем поглощение в таком цикле?

anonymous ()
Ответ на: комментарий от anonymous

Почему статические анализаторы кода отлавливают подобные ошибки без таких ограничений?

потому что другой подход. в одном случае ты пишешь код, который гарантированно лишен целого класса ошибок. в другом случае ты пишешь код с ошибками, и надеешься на статический анализатор, который и близко таких же гарантий не даст.

я понимаю, что цикл «написал - собрал - исправил ошибку» везде один и тот же. раст навязывает подход, который сокращает число таких итераций, заставляя исправлять ошибки еще на этапе проектирования типов.

MyTrooName ★★★★★ ()
Ответ на: комментарий от MyTrooName

заставляя исправлять ошибки еще на этапе проектирования типов.

Не ошибки. А любое решение, которое сложно проверить на статике средствами раста

anonymous ()
Ответ на: комментарий от anonymous

Не ошибки. А любое решение, которое сложно проверить на статике средствами раста

ошибки.

если ты абсолютно уверен, что умнее компилятора, просто пилишь unsafe

MyTrooName ★★★★★ ()
Ответ на: комментарий от anonymous

Зачем поглощение в таком цикле?

ну включи немного фантазию. представь, что у тебя каждая итерация выполняется часами, а A - ограниченный системный ресурс с эксклюзивным доступом, скажем, временный файл на винте в несколько терабайт

MyTrooName ★★★★★ ()
Ответ на: комментарий от anonymous

Твой любимый цепепе _пытается_ в move-семантику. Попутно разрешая оставлять объекты в невалидном состоянии. В C memmove тебе тоже не нужен, только deep copy на каждый чих - только хардкор?

Да я вот тоже не могу понять, зачем ты просишь комптлятор поглотить объект, но при этом того не хочешь. Разупорись.

anonymous ()
Ответ на: комментарий от anonymous

Ты небось ещё и клавиатуры за 200 рублей с жутким люфтом любишь, потому что механика с ровным вертикальным движением тебя ограничивает, да, сладенький?

anonymous ()
Ответ на: комментарий от anonymous

Ты небось ещё и клавиатуры за 200 рублей с жутким люфтом любишь, потому что механика с ровным вертикальным движением тебя ограничивает, да, сладенький?

Где ты такие клавиатуры видел? Я дешевле 1к целковых за самую обыкновенную доску в жизни не видел.

Virtuos86 ★★★★★ ()