Menu
Coddy logo textTech

From и Into

Часть раздела Объектно-ориентированное программирование путешествия по Rust на Coddy. Урок 57 из 61.

Преобразование между типами — распространённая задача в Rust. Трейт From предоставляет стандартизированный способ определить, как один тип может быть создан из другого. Когда вы реализуете From, вы автоматически бесплатно получаете трейт Into.

Чтобы реализовать From, вы определяете, как создать ваш тип из другого типа:

struct Meters(f64);
struct Kilometers(f64);

impl From<Kilometers> for Meters {
    fn from(km: Kilometers) -> Self {
        Meters(km.0 * 1000.0)
    }
}

Теперь ты можешь выполнять преобразование, используя либо функцию from, либо метод into:

let distance = Kilometers(5.0);

// Используя From явно
let m1 = Meters::from(distance);

// Используя Into (работает, потому что реализован From)
let distance = Kilometers(3.0);
let m2: Meters = distance.into();

Методу into() требуется аннотация типа, поскольку Rust должен знать, в какой тип выполняется преобразование. Этот шаблон особенно полезен, когда у тебя есть вспомогательные структуры, которые нужно преобразовать в основные типы, например преобразовать данные конфигурации в инициализированный объект или преобразовать необработанные входные данные в проверенную структуру.

challenge icon

Задание

Легко

Давайте создадим систему преобразования температуры с использованием трейта From! Вы создадите два типа температуры — Celsius и Fahrenheit — и реализуете преобразования между ними с помощью стандартных трейтов преобразования Rust.

Вы организуете код в двух файлах:

  • temperature.rs: Define две public структуры newtype — Celsius и Fahrenheit, каждая из которых содержит f64. Implement трейт From для преобразования Celsius в Fahrenheit с использованием формулы: fahrenheit = celsius × 1.8 + 32.0. Также добавьте в каждую структуру метод value, который returns внутреннее значение f64.
  • main.rs: Подключите модуль temperature и продемонстрируйте оба подхода к преобразованию. Create значение Celsius из предоставленного input, затем преобразуйте его в Fahrenheit с помощью Fahrenheit::from(). Create another значение Celsius и преобразуйте его с помощью метода .into(). Выведите оба результата.

Формула преобразования из Celsius в Fahrenheit: умножить на 1.8 и прибавить 32. Remember, что реализация From<Celsius> for Fahrenheit automatically gives вам трейт Into<Fahrenheit> для Celsius for free!

Обе температуры выводятся как целые числа: приведите каждое значение f64 с помощью as i64, что отбрасывает десятичную часть в направлении нуля. Поэтому input 36.6 выводится как 36C, а преобразованные в него 97.88 градусов Fahrenheit выводятся как 97F. Округления вверх не происходит.

Ваш вывод должен отображать оба преобразования в следующем формате:

From: {celsius1}C = {fahrenheit1}F
Into: {celsius2}C = {fahrenheit2}F

Например, для input 0 и 100:

From: 0C = 32F
Into: 100C = 212F

А для input 25 и -40:

From: 25C = 77F
Into: -40C = -40F

Вы получите два input: первое значение Celsius (parse как f64) и второе значение Celsius (parse как f64).

Попробуйте сами

mod temperature;

use temperature::{Celsius, Fahrenheit};

fn main() {
    // Прочитать ввод
    let mut input1 = String::new();
    std::io::stdin().read_line(&mut input1).expect("Failed to read line");
    let celsius1: f64 = input1.trim().parse().expect("Invalid number");
    
    let mut input2 = String::new();
    std::io::stdin().read_line(&mut input2).expect("Failed to read line");
    let celsius2: f64 = input2.trim().parse().expect("Invalid number");
    
    // TODO: Создать значение Celsius из celsius1
    // TODO: Преобразовать его в Fahrenheit используя Fahrenheit::from()
    
    // TODO: Создать другое значение Celsius из celsius2
    // TODO: Преобразовать его в Fahrenheit используя .into()
    
    // TODO: Вывести результаты в формате:
    // From: {celsius1}C = {fahrenheit1}F
    // Into: {celsius2}C = {fahrenheit2}F
}
quiz iconПроверьте себя

В этом уроке есть небольшой тест. Начните урок, чтобы ответить на вопросы и сохранить прогресс.

Все уроки раздела Объектно-ориентированное программирование

Потренируйтесь самостоятельно: Онлайн-компилятор Rust