Herança Básica
Parte da seção Programação Orientada a Objetos do Journey de Dart da Coddy — lição 36 de 110.
Herança permite que uma classe adquira as propriedades e métodos de outra classe. Em vez de reescrever o mesmo código, você cria uma nova classe que se baseia em uma já existente. A classe original é chamada de pai (ou superclasse), e a nova classe é a filha (ou subclasse).
Em Dart, você usa a palavra-chave extends para herdar de uma classe pai:
class Animal {
String name;
Animal(this.name);
void eat() {
print('$name is eating');
}
}
class Dog extends Animal {
Dog(String name) : super(name);
void bark() {
print('$name says woof!');
}
}
void main() {
var dog = Dog('Buddy');
dog.eat(); // Herdado de Animal
dog.bark(); // Definido em Dog
}A classe Dog tem acesso automático à propriedade name e ao método eat() de Animal, além de seu próprio método bark(). Isso cria uma relação "é-um" — um Dog é um Animal.
A classe filha pode adicionar novas propriedades e métodos, mas herda tudo o que é público da classe pai. Observe que membros privados (aqueles com _) não são acessíveis diretamente em subclasses de bibliotecas diferentes, embora ainda existam no objeto herdado.
Desafio
FácilVamos construir um sistema de veículos que demonstra como a herança permite que classes filhas reutilizem e estendam a funcionalidade da classe pai. Você criará uma classe pai para veículos gerais e uma classe filha para um tipo específico de veículo.
Você organizará seu código em dois arquivos:
vehicle.dart: Defina suas classes aqui:- Uma classe
Vehicle(o pai) com uma propriedadeString brand, um construtor que recebe a marca e um métodostart()que imprime'$brand engine starting...' - Uma classe
Motorcycleque estendeVehicle. Ela deve ter uma propriedade adicionalint cc(cilindrada do motor), um construtor que recebe tanto a marca quanto a cc (passando a marca para o pai usandosuper), e seu próprio métodowheelie()que imprime'$brand is doing a wheelie!'
- Uma classe
main.dart: Importe seu arquivo de veículo e demonstre a herança em ação:- Crie um
Vehiclecom a marca'Toyota' - Chame seu método
start() - Crie uma
Motorcyclecom a marca'Harley'e cc1200 - Chame o método
start()da motocicleta (herdado de Vehicle) - Chame o método
wheelie()da motocicleta (definido em Motorcycle) - Imprima
'Motorcycle engine: ${motorcycle.cc}cc'para mostrar a propriedade própria da filha
- Crie um
Observe como a classe Motorcycle ganha automaticamente acesso à propriedade brand e ao método start() de Vehicle, ao mesmo tempo em que possui sua própria propriedade cc e o método wheelie() exclusivos. Este é o poder da herança - construir sobre o código existente.
Saída esperada:
Toyota engine starting...
Harley engine starting...
Harley is doing a wheelie!
Motorcycle engine: 1200ccFolha de consulta
Use a palavra-chave extends para criar uma classe filha que herda de uma classe pai:
class Animal {
String name;
Animal(this.name);
void eat() {
print('$name is eating');
}
}
class Dog extends Animal {
Dog(String name) : super(name);
void bark() {
print('$name says woof!');
}
}A classe filha herda todas as propriedades e métodos públicos da classe pai. Use super no construtor da classe filha para passar parâmetros para o construtor da classe pai.
As classes filhas podem adicionar suas próprias propriedades e métodos, enquanto ainda acessam os herdados:
var dog = Dog('Buddy');
dog.eat(); // Herdado de Animal
dog.bark(); // Definido em DogIsso cria uma relação do tipo "é um" - um Dog é um Animal.
Experimente você mesmo
import 'vehicle.dart';
void main() {
// TODO: Criar um Vehicle com a marca 'Toyota'
// TODO: Chamar o método start() do veículo
// TODO: Criar uma Motorcycle com a marca 'Harley' e cc 1200
// TODO: Chamar o método start() da motocicleta (herdado de Vehicle)
// TODO: Chamar o método wheelie() da motocicleta
// TODO: Imprimir 'Motorcycle engine: [cc]cc' usando a propriedade cc da motocicleta
}
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
1Fundamentos de POO
Arquivos ExternosBibliotecas e ImportaçõesIntrodução à POOClasses vs ObjetosA Palavra-chave thisMétodosVariáveis de InstânciaFundamentos de ConstrutoresRecapitulação - Calculadora Simples4Null Safety
Introdução ao Null SafetyNullable vs Non-NullableOs Operadores ? e !Palavra-chave Late e Null SafetyOperadores Null-AwareNull Safety em ClassesRecapitulação - Sistema de Perfil de Usuário7Classes Abstratas e Interfaces
Classes AbstratasMétodos AbstratosInterfaces em DartInterfaces ImplícitasImplementando vs EstendendoMúltiplas InterfacesRecapitulação - Calculadora de Formas10Coleções e Generics
Visão Geral de List, Set e MapColeções Type-SafeClasses GenéricasMétodos GenéricosRestrições de GenericsIterable e IteratorRecapitulação - Armazenamento Genérico13Conceitos Avançados de POO
Composição vs HerançaMétodos de ExtensãoClasses ChamáveisClasses Seladas (Dart 3)Records (Dart 3)Patterns & Matching (3.0)Enums com Métodos16Projeto: Gerenciamento de Biblioteca
Visão Geral do ProjetoClasses Livro e Usuário2Construtores em Dart
Construtor PadrãoConstrutores NomeadosListas de InicializaçãoConstrutores ConstantesConstrutores FactoryConstrutores de RedirecionamentoRecapitulação - Shape Builder5Encapsulamento
Membros Públicos vs PrivadosA Convenção do Prefixo _Privacidade em Nível de BibliotecaAprofundamento em Getters & SettersOcultação de InformaçãoRecapitulação - Registros de Estudantes8Mixins
Introdução aos MixinsCriando MixinsUsando Múltiplos MixinsPalavra-chave on em MixinsMixin vs HerançaMixin vs InterfaceRecapitulação - Sistema Animal11Métodos Especiais
Sobrescrita de toString()Sobrescrita de hashCode & ==Interface ComparableMétodo call()Sobrescrita de noSuchMethodRecapitulação - Coleção Personalizada14Padrões de Projeto Parte 1
Introdução aos Padrões de ProjetoPadrão SingletonPadrão FactoryPadrão ObserverPadrão Strategy3Propriedades de Classe
Membros de Instância vs EstáticosCampos Final & ConstVariáveis LateMétodos e Campos EstáticosGetters e SettersRecapitulação - Gerenciador de Conta Bancária6Herança
Herança BásicaA Palavra-chave superSobrescrita de MétodoA Anotação @overrideA Palavra-chave final para ClassesConstrutores e HerançaRecapitulação - Hierarquia de Funcionários9Polimorfismo
Fundamentos do PolimorfismoPolimorfismo via InterfacesVerificação de Tipos em Tempo de ExecuçãoOs Operadores is & asPalavra-chave CovariantRecapitulação - Processador de Pagamentos12POO Assíncrona
Futures e async/awaitFundamentos de StreamsStream ControllersConstrutores AssíncronosAsync em Métodos de ClasseRecapitulação - Data Fetcher15Padrões de Projeto Parte 2
Padrão CommandPadrão AdapterPadrão DecoratorPadrão Template MethodPadrão StatePadrão CompositePadrão Repository