Взглянем:
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 говорит :
Из T для U подразумевается In U для T
Хотя usize -> u128 выглядит нормально, u128 -> usize нет. Хорошо, но почему вместо usize не реализовано Into<u128>?
Ответ 1 · рейтинг 5 · Masklinn
Хотя usize -> u128 выглядит нормально, u128 -> usize - нет. Хорошо, но почему Into не реализован для использования вместо этого?
Потому что, несмотря на то, что для Rust гарантируется, что usize всегда будет не менее 16 бит, не гарантируется, что он всегда будет максимум 64 бита.
Маловероятно, что это когда-либо будет полезно, но технически ничто не препятствует 256-битным указателям, а поскольку размер usize гарантированно соответствует размеру указателя, это сделает преобразование usize -> u128 невозможным.
Ответ 2 · whilrun
В документе 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();
}