A fim de entender realmente os benefícios associados com a encapsulação, iremos analisar a seguir um exemplo onde encapsulação não é utilizada, e possíveis problemas que podem ocorrer neste caso. Posteriormente, este problema será revisitado para analisar uma solução com encapsulação.
Neste problema, duas entidades são consideradas. A primeira delas é uma entidade do tipo retângulo, que tem uma altura e uma largura. A área do retângulo pode ser calculada como o produto destes dois valores. A segunda entidade é uma entidade do tipo mastro, que tem um comprimento e uma profundidade (o quanto o mastro foi enterrado); o comprimento total do mastro é a soma destes dois valores.
A solução usando ANSI-C seria representar cada uma das entidades como uma estrutura. Esta solução é apresentada a seguir.
indentation
The area of the box is 120 The area of the square is 64 The funny area is 80 The bad area is 48
Embora esta situação possa parecer tola quando observada neste pequeno exemplo, ela pode ocorrer com frequência em sistemas de porte maior. Não há modos de prevenir que isto aconteça em ANSI-C. A solução real para este problema está na encapsulação.
O exemplo a seguir ilustra a utilização de classes para modelar o mesmo problema. Retângulo é agora modelado como uma classe. Neste caso torna-se evidente que o cálculo de área é algo que só faz sentido (neste caso) para retângulos, pois o método correspondente é uma função membro desta classe. Mastro ainda é modelado como uma estrutura apenas para ilustrar que os dois tipos de construções podem coexistir sem problemas em um programa.
indentation
The area of the box is 120 The area of the square is 64
Observe que não há modo, neste caso, de cometer os enganos que ocorriam no exemplo anterior -- simplesmente é impossível acessar diretamente os dados de objetos individuais da classe retângulo e, consequentemente, é impossível misturar a informação que eles carregam.
Esta técnica não é exatamente inédita. Sistemas operacionais usualmente adotam o conceito de kernel, um conjunto de serviços que pode apenas ser acessado através de rotinas pré-estabelecidas (system calls). A manipulação de arquivos é um exemplo de um destes serviços. A fim de manipular arquivos, o sistema operacional mantém um grande conjunto de dados. Entretanto, o usuário nem sabe da existência destes dados -- tudo o que ele pode fazer é requisitar os serviços através do system call adequado. Isto evita que o usuário, inadvertidamente, corrompa o sistema de arquivos.
A definição de classes permite que o programador use este mesmo mecanismo na implementação de uma aplicação. No exemplo anterior, a definição da classe retângulo e de seus métodos poderia ter sido desenvolvida à parte, de forma totalmente isolada do programa que a utiliza. Uma vez que esta classe esteja desenvolvida e ``aprovada'', ela pode tornar-se disponível para ser utilizada na aplicação. Observe como a utilização de classes promove de modo natural a técnica de dividir para conquistar. Em grandes projetos, esta abordagem é repetidamente utilizada, sendo que algumas classes podem ser extremamente complexas internamente -- mas para o usuário da classe esta complexidade é totalmente abstraída.