'Coupling' é um termo que descreve o relacionamento entre duas entidades em um sistema de software (geralmente classes).
Quando uma classe usa outra classe ou se comunica com ela, diz-se que "depende" dessa outra classe e, portanto, essas classes são "acopladas". Pelo menos um deles 'sabe' sobre o outro.
A idéia é que devemos tentar manter o acoplamento entre as classes em nossos sistemas o mais "frouxo" possível: portanto, "frouxo" ou, às vezes, "desacoplamento" (embora em inglês "desacoplamento" significasse "nenhum acoplamento", as pessoas use-o frequentemente para implicar um 'acoplamento flexível' entre entidades).
Então: o que é acoplamento flexível versus acoplamento forte na prática, e por que devemos tornar as entidades acopladas livremente?
O acoplamento descreve o grau de dependência entre uma entidade e outra. Frequentemente classes ou objetos.
Quando a classe A depende muito da classe B, as chances de a classe A ser afetada quando a classe B é alterada são altas. Este é um acoplamento forte.
No entanto, se a ClassA depende ligeiramente da ClassB, as chances de a ClassA ser afetada de alguma forma por uma alteração no código da ClassB são baixas. Isso é um acoplamento frouxo ou um relacionamento "desacoplado".
O acoplamento frouxo é bom porque não queremos que os componentes do nosso sistema dependam fortemente um do outro. Queremos manter nosso sistema modular, onde podemos alterar com segurança uma parte sem afetar a outra.
Quando duas partes são fracamente acopladas, elas são mais independentes uma da outra e têm menos probabilidade de quebrar quando a outra muda.
Por exemplo, ao construir um carro, você não deseja que uma mudança interna no motor quebre algo no volante.
Embora isso nunca aconteça por acidente na construção de um carro, coisas semelhantes acontecem com os programadores o tempo todo. O acoplamento frouxo visa reduzir o risco de tais coisas acontecerem.
Acoplamento forte geralmente ocorre quando a entidade A sabe muito sobre entidade B. Se a entidade A faz muitas suposições sobre como entidade B opera ou como ele é construído, do que há um alto risco de que uma mudança na entidade B afetará entidade A. Este é porque uma de suas suposições sobre a entidade B agora está incorreta.
Por exemplo, imagine que, como motorista, você faça algumas suposições sobre como o motor do seu carro funciona.
No dia em que você compra um carro novo com um motor que funciona de maneira diferente (ou por algum motivo, seu motor foi substituído), suas suposições anteriores estavam incorretas. Se você fosse um código em um computador, agora seria um código incorreto que não funciona corretamente.
No entanto, se todas as suposições que você, como motorista, fez sobre os carros são: A- eles têm volantes e B- eles têm pedais de freio e acelerador, as mudanças no carro não afetam você, desde que suas poucas suposições fique correto. Este é um acoplamento frouxo.
Uma técnica importante para obter acoplamentos soltos é o encapsulamento. A idéia é que uma classe oculte seus detalhes internos de outras classes e ofereça uma interface estritamente definida para que outras classes se comuniquem com ela.
Assim, por exemplo, se você estivesse definindo uma classe de carro, sua interface (métodos públicos) seria provavelmente drive()
, stop()
, steerLeft()
, steerRight()
, getSpeed()
. Esses são os métodos que outros objetos podem invocar nos objetos Car.
Todos os outros detalhes da classe Car: como o motor funciona, tipo de combustível usado etc. estão ocultos de outras classes - para impedir que eles saibam muito sobre o Car.
No momento em que a classe A sabe muito sobre a classe B: temos um relacionamento fortemente associado, em que a classe A é muito dependente da classe B e uma mudança na classe B provavelmente afeta a classe A. Tornando o sistema difícil de expandir e manter.
Um relacionamento entre duas entidades, onde eles sabem pouco um do outro (apenas o necessário) - é um relacionamento fracamente acoplado ou dissociado.