Menu
Coddy logo textTech

Реализация трейтов

Часть раздела Object Oriented Programming путешествия по Rust на Coddy. Урок 30 из 61.

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

Синтаксис использует impl TraitName for StructName:

trait Speak {
    fn speak(&self) -> String;
}

struct Dog {
    name: String,
}

impl Speak for Dog {
    fn speak(&self) -> String {
        format!("{} says: Woof!", self.name)
    }
}

Блок impl Speak for Dog сообщает Rust, что Dog реализует типаж Speak. Внутри вы предоставляете фактическое тело метода — именно здесь вы определяете, как говорит собака.

Сила типажей становится очевидной, когда несколько типов реализуют один и тот же типаж:

struct Cat {
    name: String,
}

impl Speak for Cat {
    fn speak(&self) -> String {
        format!("{} says: Meow!", self.name)
    }
}

Теперь и Dog, и Cat обладают способностью Speak, но каждый предоставляет свою собственную уникальную реализацию. Вы можете вызвать .speak() для любого из этих типов:

let dog = Dog { name: String::from("Rex") };
let cat = Cat { name: String::from("Whiskers") };

println!("{}", dog.speak());  // Rex говорит: Woof!
println!("{}", cat.speak());  // Whiskers говорит: Meow!

Это основа полиморфизма в Rust — разные типы, один и тот же интерфейс, уникальное поведение.

challenge icon

Задание

Легко

Давайте воплотим типажи (traits) в жизнь, реализовав их для различных типов! Вы создадите типаж Describable и реализуете его для двух разных структур, каждая из которых будет предоставлять свое уникальное описание.

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

  • describable.rs: Определите публичный типаж Describable с методом describe(&self) -> String.
  • items.rs: Создайте две публичные структуры, которые реализуют ваш типаж:
    • Book с публичным полем title (String)
    • Movie с публичным полем name (String)
    Каждая структура должна реализовывать Describable со своим собственным уникальным форматом описания.
  • main.rs: Объедините ваши модули, создайте экземпляры обеих структур и вызовите их методы describe, чтобы показать, как один и тот же типаж выдает разные результаты для разных типов.

Ваша структура Book должна описывать себя как Book: {title}, а ваша Movie должна описывать себя как Film: {name}. Обратите внимание, как каждый тип выполняет один и тот же контракт, но со своим собственным поведением!

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

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

Book: {title}
Film: {name}

Например, при входных данных 1984 и Inception:

Book: 1984
Film: Inception

Вы получите два входных значения: название книги и название фильма.

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

mod describable;
mod items;

use describable::Describable;
use items::{Book, Movie};

fn main() {
    // Чтение входных данных
    let mut title = String::new();
    std::io::stdin().read_line(&mut title).expect("Failed to read line");
    let title = title.trim().to_string();
    
    let mut name = String::new();
    std::io::stdin().read_line(&mut name).expect("Failed to read line");
    let name = name.trim().to_string();
    
    // TODO: Создать экземпляр Book с названием title
    
    // TODO: Создать экземпляр Movie с названием name
    
    // TODO: Вывести описание книги
    
    // TODO: Вывести описание фильма
}
quiz iconПроверьте себя

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

Все уроки раздела Object Oriented Programming

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