O problema que o padrão resolve
Imagine um sistema de notificações que envia e-mail ou SMS. Se a lógica de negócio instancia diretamente EmailNotificador, cada nova forma de envio exige editar o fluxo que deveria apenas preparar e enviar uma notificação. Factory Method define um método de criação cuja implementação escolhe o produto concreto, mantendo o código cliente dependente de uma abstração.
Exemplo em C#
public interface IExportador
{
string Exportar(string conteudo);
}
public abstract class Relatorio
{
public string Gerar(string dados)
{
var exportador = CriarExportador();
return exportador.Exportar(dados);
}
protected abstract IExportador CriarExportador();
}
public sealed class RelatorioCsv : Relatorio
{
protected override IExportador CriarExportador() => new CsvExportador();
}
public sealed class RelatorioJson : Relatorio
{
protected override IExportador CriarExportador() => new JsonExportador();
}O método Gerar define o fluxo estável e chama uma fábrica extensível. Em uma aplicação moderna, a variação pode ser selecionada pela composição de dependências em vez de uma hierarquia de subclasses; preserve a intenção sem copiar o desenho clássico se DI já resolver o problema com menos código.
Quando usar e quando evitar
Use quando subclasses ou implementações realmente variam o tipo criado e o fluxo cliente não deve conhecer essa escolha. Evite quando há apenas uma implementação ou quando um construtor simples já deixa a intenção mais clara. O padrão desloca a decisão; não elimina a necessidade de decidir configuração e ciclo de vida.
Relação com outros padrões
Abstract Factory cria famílias de produtos relacionados; Factory Method decide um tipo de produto por método de criação. Builder resolve construção passo a passo, não seleção de família. Veja também o guia dos 23 Design Patterns GoF e os princípios de SOLID.