Você começa seu projeto limpo, modular, bonito. E antes mesmo de escrever sua primeira linha de lógica, lá está ele:
uses
System.SysUtils,
MyApp.Utils,
Math;
ou
import os
import sys
from pathlib import Path
E pronto. Já era. Você acabou de acoplar seu código a três dependências externas.
Não importa se vai usar uma única função de cada uma delas. Elas já estão acopladas ao seu contexto.
Mas por que isso importa?
Porque dependência é um tipo especial de acoplamento. E quanto mais dependências diretas seu código possui, menor sua portabilidade, maior sua fragilidade e mais difícil o reuso.
E, pior: você talvez nem saiba que está acoplando até dar erro em produção.
Existem linguagens que importam só o necessário?
Sim... e não. Linguagens como Go, Rust e até o JavaScript moderno (ES Modules) têm estratégias para minimizar isso:
- Go é famoso por não permitir importações não utilizadas. Se você importar um pacote e não usar nada dele, o compilador reclama.
- Rust permite importações altamente seletivas:
use std::fs::File; // Só a structure File
use std::io::Read; // Só a trait Read
- JavaScript (ES6+) permite importações de partes específicas:
import { readFile } from 'fs';
Mas nenhuma dessas linguagens impede totalmente o acoplamento. Elas apenas te permitem modularizar melhor — e, em alguns casos, facilitam a tree shaking (remoção de código morto na hora de empacotar).
A real: até sua linguagem está contra você
Mesmo que você só use uma função de um módulo, muitas vezes a classe inteira é carregada. Isso depende de como o linker, runtime ou compilador da linguagem funciona.
Por exemplo, em Delphi ou C++ tradicional, uses
ou #include
pode trazer todo o conteúdo da unit ou header para dentro do seu binário. Em linguagens mais modernas, como Rust ou JavaScript com Webpack/Vite, há mais inteligência no empacotamento, mas o princípio do acoplamento ainda existe.
E o que dá pra fazer com isso?
A resposta é simples e brutal:
Você não pode evitar acoplamento, mas pode entender onde ele começa e controlar sua propagação.
- Evite
uses
em units grandes só para usar uma função. - Crie interfaces e abstrações para modularizar dependências reais.
- Prefira módulos pequenos, com responsabilidade única.
- Use injeção de dependência com parcimônia — não como religião.
O que é acoplamento de verdade?
Acoplamento real não é só quando um objeto chama o método de outro.
Acoplamento real é quando uma parte do seu código depende da existência, comportamento ou assinatura de outra parte — de forma rígida, explícita ou implícita.
Acoplamento começa na sua primeira linha. A diferença é se você está ciente disso ou não.
Conclusão
Da próxima vez que você digitar uses
, import
ou include
, lembre-se:
Você está abrindo a porta para um pacote inteiro entrar na sua casa.
Pode vir só uma função — ou pode vir um elefante junto.
E se der ruim, não adianta dizer que não foi você quem chamou.