Почему преобразование usize в u128 в Rust считается неудачным? - PullRequest
2 голосов
/ 10 июля 2020

Взгляните:

use std::convert::{From, TryFrom};

fn main() {
  let size: usize = 42;
  let good: u128  = u128::try_from(size).unwrap(); // works fine
  let bad:  u128  = u128::from(size);              // doesn't compile!
}

Насколько я знаю, usize - это целочисленный тип, и они никогда не превышают 128 бит. Поэтому я не вижу, чтобы преобразование usize -> u128 могло завершиться ошибкой. Итак, почему u128 не реализует From<usize>?

Обновление : документация Rust говорит:

From T for U означает Into U для T

Хотя usize -> u128 кажется нормальным, u128 -> usize - нет. Хорошо, но почему вместо Into<u128> не реализовано usize?

Ответы [ 2 ]

3 голосов
/ 10 июля 2020

Хотя usize -> u128 кажется нормальным, u128 -> usize - нет. Хорошо, но почему вместо этого для usize не реализован Into? 1005 * не более 64 бита.

Это кажется маловероятным, но технически ничто не препятствует использованию 256-битных указателей, а поскольку usize гарантированно будет иметь размер указателя, преобразование usize -> u128 станет невозможным .

0 голосов
/ 10 июля 2020

В документе From trait написано

Примечание: эта черта не должна терпеть неудачу. Если преобразование может завершиться неудачно, используйте TryFrom.

Поскольку вы не будете знать, может ли usize содержать значение u16 / u32 / u64 / u128 (в зависимости от цели компиляции), все эти примитивные типы реализуют TryFrom вместо From.

В документе Rust implies означает, что когда у вас есть тип, реализует From, компилятор бесплатно выдаст вам Into (обратите внимание, что обратное неправда). Та же идея применима к TryFrom и TryInto. Таким образом, следующий код будет работать должным образом.

use std::convert::{TryFrom,TryInto};

fn main() {
  let size: usize = 42;
  let good: u128  = u128::try_from(size).unwrap();
  let doublegood:usize = good.try_into().unwrap();
}
...