Menu
Coddy logo textTech

Usando Múltiplos Traits

Parte da seção Programação Orientada a Objetos do Journey de PHP da Coddy. Lição 52 de 91.

Uma única trait é útil, mas o verdadeiro poder surge quando você combina várias traits em uma classe. O PHP permite incluir quantas traits forem necessárias, dando à sua classe capacidades de várias fontes ao mesmo tempo.

Para usar múltiplos traits, basta listá-los separados por vírgulas após a palavra-chave use:

<?php
trait Timestampable {
    public function getTimestamp(): string {
        return date('Y-m-d H:i:s');
    }
}

trait Identifiable {
    private string $id;
    
    public function generateId(): void {
        $this->id = uniqid('id_');
    }
    
    public function getId(): string {
        return $this->id;
    }
}

class Post {
    use Timestampable, Identifiable;
    
    public function __construct(public string $title) {
        $this->generateId();
    }
}

$post = new Post("Hello World");
echo $post->getId() . " - " . $post->getTimestamp();

Saída:

id_6789abc123 - 2024-01-15 10:30:00

A classe Post agora tem métodos de ambas as traits. Cada trait contribui com sua própria funcionalidade — Timestampable fornece métodos relacionados ao tempo, enquanto Identifiable lida com IDs exclusivos. Essa abordagem mantém cada trait focada em uma única responsabilidade, tornando seu código mais modular e reutilizável.

O que acontece quando duas traits têm métodos com o mesmo nome? Essa é uma situação de conflito que exploraremos na próxima lição.

challenge icon

Desafio

Fácil

Vamos criar um sistema de gerenciamento de produtos que combina múltiplas traits para oferecer aos produtos recursos de precificação e controle de estoque. Cada trait lidará com uma única responsabilidade, e sua classe de produto obterá funcionalidades de ambas.

Você organizará seu código em três arquivos:

  • Priceable.php: Crie uma trait chamada Priceable que lide com a funcionalidade de precificação. A trait deve ter:
    • Uma propriedade privada $price (float)
    • Um método setPrice(float $price) que armazene o preço
    • Um método getPrice() que retorne o preço
    • Um método getFormattedPrice() que retorne o preço formatado como "$[price]" com 2 casas decimais
  • Stockable.php: Crie uma trait chamada Stockable que gerencie o estoque. A trait deve ter:
    • Uma propriedade privada $stock (integer)
    • Um método setStock(int $quantity) que armazene a quantidade em estoque
    • Um método getStock() que retorne o estoque atual
    • Um método isInStock() que retorne true se o estoque for maior que 0, e false caso contrário
  • main.php: Inclua os dois arquivos de trait e crie uma classe Product que use as traits Priceable e Stockable. Use a promoção de construtor para definir uma propriedade pública $name. O construtor também deve aceitar um preço e uma quantidade em estoque, usando os métodos das traits para defini-los.

    Você receberá três entradas: o nome de um produto, um preço e uma quantidade em estoque. Crie um produto com esses valores e imprima quatro linhas:

    • O nome do produto
    • O preço formatado (usando getFormattedPrice())
    • A quantidade em estoque
    • "Available" se houver estoque, ou "Out of stock" caso contrário

Isso demonstra como várias traits trabalham juntas. Sua classe Product obtém recursos de precificação de uma trait e gerenciamento de estoque de outra, mantendo cada responsabilidade devidamente separada enquanto as combina em um produto completo.

Experimente você mesmo

<?php
require_once 'Priceable.php';
require_once 'Stockable.php';

// TODO: Crie uma classe Product que use ambas as traits Priceable e Stockable
// Use promoção de construtor para a propriedade pública $name
// O construtor deve aceitar name, price e stock, e usar métodos das traits para definir price e stock

class Product {
    // TODO: Use as traits aqui

    // TODO: Implemente o construtor com promoção de construtor para $name
    // e defina price e stock usando métodos das traits
}

// Ler entrada
$name = trim(fgets(STDIN));
$price = floatval(trim(fgets(STDIN)));
$stock = intval(trim(fgets(STDIN)));

// TODO: Crie uma instância de Product com os valores de entrada

// TODO: Imprima o nome do produto
// TODO: Imprima o preço formatado usando getFormattedPrice()
// TODO: Imprima a quantidade em estoque
// TODO: Imprima "Available" se em estoque, ou "Out of stock" se não
?>
quiz iconTeste seus conhecimentos

Esta lição inclui um quiz rápido. Comece a lição para respondê-lo e acompanhar seu progresso.

Todas as lições de Programação Orientada a Objetos

Pratique por conta própria: Compilador de PHP online