Eu tenho uma classe que calcula a renda anual líquida dos trabalhadores. Tem uma constante que representa uma porcentagem de imposto. Mas um dia a taxa de imposto mudou, então preciso corrigir o código.
O ato de fixar essa constante indica uma violação do Princípio Aberto-Fechado , uma vez que postula que uma classe deve ser fechada para modificação?
object-oriented
object-oriented-design
solid
Paradisys de Análise
fonte
fonte
Respostas:
O OCP pode ser melhor compreendido quando se pensa em classes ou componentes fornecidos por um fornecedor A em algum tipo de caixa preta, para uso dos usuários B, C e D (observe que este é apenas um modelo mental que estou usando para maior clareza, não importa se, na realidade, o único usuário da classe é o próprio A).
Se B, C e D puderem usar ou reutilizar as classes fornecidas para diferentes casos de uso, sem a necessidade de modificação do código-fonte da biblioteca, o componente atenderá ao OCP ( em relação a uma categoria de casos de uso ). Existem diferentes meios para conseguir isso, como
tornando a classe herdável (geralmente em conjunto com o padrão de método de modelo ou o padrão de estratégia)
fornecendo "pontos de injeção" para injeção de dependência
fornecendo parâmetros de configuração para a classe ou componente (por exemplo, tendo um parâmetro do construtor "porcentagem de imposto", como no seu caso, ou usando outro mecanismo de configuração)
talvez outros meios, dependendo da linguagem de programação ou ecossistema
Os exemplos típicos que você encontra nos livros didáticos geralmente são do primeiro ou do segundo tipo (acho que, aos olhos dos autores desses livros, o terceiro tipo é trivial demais para ser mencionado).
Como você vê, isso não tem nada a ver com proibir qualquer alteração do código-fonte pelo fornecedor A (como correção de erros, otimização ou adição de novos recursos de uma maneira compatível com versões anteriores), que não tem nenhuma relação com o OCP. O OCP é sobre como A projeta a interface e a granularidade dos componentes na lib, para que diferentes cenários de reutilização (como resuage com diferentes taxas de imposto) não induzam automaticamente requisitos de mudança.
Portanto, apesar do que os outros lhe disseram aqui, a resposta é claramente "sim" , seria uma violação do OCP.
EDIT: parece que entre alguém escreveu um post detalhado sobre exatamente esse tópico. Embora algumas partes possam ter sido melhor formuladas (como Derek Elkins apontou), parece que o autor geralmente compartilha do meu ponto de vista que "cumprir o OCP" não é uma propriedade absoluta, mas algo que só pode ser avaliado no contexto de certas categorias de alterações de requisitos.
fonte
Como outros dizem, idealmente, a classe de renda do trabalhador permitiria a parametrização da constante, tornando essa classe independente desse valor.
Por fim, o aplicativo de chamada também pode permitir a parametrização em termos de configuração externa (por exemplo, um arquivo). Assim que tivermos uma configuração externa, podemos alterar a taxa de imposto - embora considere que, se o arquivo de configuração for lido apenas uma vez na inicialização, o aplicativo precisará ser reiniciado para que as porcentagens de impostos atualizadas entrem em vigor, portanto é algo a manter mente. Poderíamos fornecer um recurso de aplicativo para reler a configuração quando solicitado, ou fornecer um mecanismo mais complicado que notará quando o arquivo de configuração é alterado ...
A longo prazo, você pode achar que as questões tributárias exigem mais do que apenas uma porcentagem - por exemplo, que um dia as leis tributárias são mais complexas e exigem várias porcentagens e algumas constantes (por exemplo, o valor abaixo de US $ 10 mil tributado em X%, enquanto o restante tributado em Y%).
Isso basicamente sugere o uso de um padrão de estratégia, em que a classe principal em questão aqui aceita um objeto de estratégia para calcular o imposto.
As várias estratégias (e% 's e $ constantes) devem ser escolhidas no arquivo de configuração e, agora, adicionar uma nova estratégia exige a adição de um novo código, mas não necessariamente a atualização do código existente.
Cada estratégia pode saber como analisar / interpretar seus próprios argumentos de configuração externa, além de como calcular o imposto real.
Dinamicamente, o imposto pode depender ainda mais do código de idioma do governo, portanto, você pode ter um código de idioma associado a ganhos ou a funcionários (ou ambos). Na configuração externa, podemos associar localidade à estratégia tributária.
Veja também injeção de dependência , onde gerenciamos essas coisas explicitamente.
fonte
Se você precisar modificar a classe para alterar o valor do imposto, seu design estará violando o OCP. O design apropriado, para o que você descreveu até agora, é que a classe da calculadora tome o valor do imposto como parâmetro.
Se sua classe for instanciada (o que significa que não é uma classe estática), tornando a propriedade da classe variável de imposto, cujo valor é injetado pelo construtor, você também estará melhorando a coesão da classe.
Em resumo, seu design atual faz com que sua classe dependa de um valor constante que não seja realmente constante (definindo constante como um valor que nunca mudaria, independentemente do que fosse, como o valor do PI). Viola o OCP. Altere o design para receber o valor do imposto como argumento do construtor.
fonte
Concordo totalmente com o @Becuzz, e só quero resumir: OCP é sobre encontrar abstrações reutilizadas (portanto úteis) que são injetadas em uma classe. Portanto, o comportamento da classe é modificado não alterando seu código, mas fornecendo diferentes implementações. Isso fica claro no livro de Robert Martin " Desenvolvimento, princípios, padrões e práticas de software ágil ", verifique o capítulo correspondente "O princípio de abertura e fechamento", subcapítulo "Abstração é a chave". Esclarece outro equívoco de que o comportamento pode ser modificado apenas com herança. Foi Bertrand Meyer quem propôs isso em 1988 em seu livro " Construção de software orientada a objetos ", não Robert Martin.
fonte
A meu ver, não é uma violação do princípio aberto e fechado. No entanto, o fato de que algo que pode mudar no tempo (como a porcentagem de imposto) é uma constante é uma falha de design: você não deve alterar o valor da constante, mas como lida com a porcentagem de imposto. Deve ser algum tipo de configuração que pode ser modificada sem recompilar tudo.
fonte