Como você aborda o design de classe em OOPs?

12

Quando tento projetar uma solução OO, geralmente uso a modelagem CRC, na qual listo os nomes das classes (substantivos), o que eles fazem (verbos) e como eles colaboram com outras classes.

Este blog tem o seguinte a dizer sobre essa abordagem substantivo-verbo

   ...This approach, which I will call “noun and verb,” is so limited 
   I’ll dare to call it brain damaged....

Minha pergunta é: existe uma melhor técnica de modelagem para usar a abordagem OO?

Vinoth Kumar CM
fonte
1
Supondo que o lance $$$ faça sentido, basta começar a codificar. Quando preso, encontre uma maneira de remover obstáculos. Re-fator mais tarde. "CRC" não é algo que eu já tenha ouvido antes, mas isso não me impediu de escrever aulas. Se houvesse um grande princípio mecânico por aí, alguém teria criado uma boa ferramenta de análise de código e seria popular. Até encontrar algo assim, continuarei usando minha intuição. Claro, ele tem que usar verbos e substantivos nos lugares certos ...
1
Yeesh. Basta obter um modelo mental rápido do sistema e começar a escrever o código. Sei que muitos vão discordar de mim aqui, mas você pode analisar demais essas coisas até a morte. Contanto que você tenha uma quantidade razoável de experiência, deve ter uma idéia do que vai e não vai funcionar. Se for difícil trabalhar com algo cedo, mude-o, e agora você tem ainda mais experiência.
Ed4

Respostas:

12

Para ser justo, ele acrescentou "Divertido" a essa afirmação.

Até hoje, começo a modelar sistemas usando a abordagem "substantivo e verbo", mas, ao longo dos anos, descobri que o TDD nos ensina que essa abordagem chama sua atenção para a coisa errada. Nesse sentido, o blogueiro tem razão. No entanto, não tenho certeza de que seja a abordagem errada, e não o modo como nossas mentes funcionam.

Se você quiser tentar um pequeno desafio aqui, pare de ler e tente modelar o jogo Monopoly, usando o idioma inglês, e volte aqui.

Suspeito que a tentação será olhar imediatamente para os objetos com os quais interagimos muito - o tabuleiro, os espaços, as cartas, os dados, as peças - mas não é para lá que vai a maior parte da lógica. A maioria desses objetos é totalmente burra. Dados, se você quiser.

Mas assim que você começa a escrever testes, percebe qual objeto é de longe o mais importante em qualquer jogo: as regras.

Lembra-se daquele pequeno pedaço de papel que você leu uma vez no jogo e não interage novamente até que haja uma disputa? A versão computadorizada não funciona dessa maneira. Cada coisa que o jogador tenta fazer, um computador consulta as regras e verifica se é permitido ou não fazer isso.

Quando você pensa sobre isso, você faz a mesma coisa, mas como leva tempo para ler as regras em papel e seu cérebro possui um sistema de armazenamento em cache razoável, você consulta as regras em sua cabeça. Um computador provavelmente achará tão fácil ler as regras novamente - a menos que elas estejam armazenadas no banco de dados; nesse caso, elas também poderão ser armazenadas em cache.

E é por isso que o TDD é tão popular na condução do design. Porque ele tende a direcionar seu processo de pensamento rapidamente para os lugares certos:

Quando penso que vou escrever alguns testes para o meu jogo de monopólio. Eu posso olhar para o meu aparelho e tentar encontrar os objetos. Então, nós temos essas peças. Vou escrever alguns testes para eles.

Talvez eu tenha uma classe base MonopolyPiece e cada tipo de peça derivará delas. Vou começar com o DogPiece. Primeiro teste ... ahh. Na verdade, não há lógica aqui. Sim, cada peça será desenhada de maneira diferente, por isso posso precisar de um DogDrawer, mas enquanto estou desenvolvendo o jogo, só quero escrever "D" na tela. Vou apimentar a interface do usuário no final.

Vamos encontrar alguma lógica real para testar. Existem muitas casas e hotéis, mas eles não precisam de testes. Dinheiro não. Cartões de propriedade, não. E assim por diante. Até a placa nada mais é do que uma máquina de estado, não contém nenhuma lógica.

Você descobrirá rapidamente que ainda tem três coisas em sua mão. As cartas Chance e Community Chest, um par de dados e um conjunto de regras. Essas serão as partes importantes para projetar e testar.

Você viu isso chegando quando escreveu os substantivos e verbos?

De fato, há um ótimo exemplo nos Padrões e Práticas de Princípios Ágeis de Robert Martin, em que eles tentam desenvolver um aplicativo Bowling Score Card usando TDD e encontram todo tipo de coisas que pensavam que eram classes óbvias, que simplesmente não valiam a pena se preocupar.

pdr
fonte
Não consigo entender por que o TDD é uma resposta para fazer a análise de OO que o OP está perguntando. Substantivo / verbo é a primeira aproximação do domínio do problema (mais útil para iniciantes) e, é claro, refinar as classes pode ser feito mais tarde, mas a afirmação que o TDD direciona o design na direção certa é IMHO completamente errada (você realmente sugere que pule o planejamento , crie e comece a codificar ?!). O exemplo de monopólio também é enganoso, dependendo da parte do sistema em que você está trabalhando: interface do usuário ou lógica principal. Na interface do usuário corta e outros enfeites fazem todo sentido.
Roman Susi
+1 e favorito. Primeiro, minha experiência é que o TDD direciona seu processo de pensamento rapidamente para os lugares certos (bem, às vezes você pode discutir "rapidamente"). E também pode ajudar a revelar defeitos de design: você aprenderá a injeção de dependência, se nada mais! Substantivo - quem não começa aqui? Mas a maioria desses objetos é totalmente burra. Dados, se você quiser, é profundo. O título de um livro seminal diz tudo para mim Estruturas Algoritmos + dados = Programas
radarbob
3

Eu nunca achei esses métodos úteis para mim. Na verdade, eu achei que usá-los apenas me confunde pior. Confira a cafeteira de Robert C. Martin , também não acho que ele use esse tipo de abordagem.

Uma coisa que me incomoda logo é a solução que a pessoa encontra no artigo da CRC ao qual você vincula. A colaboração entre Cliente / Pedido não é algo que eu consideraria interessante, mas não está escrito de qualquer maneira. Não há nada de particularmente interessante nesse modelo sobre um Cliente que mereça status de classe. A única coisa interessante de ser um "cliente" é que há um ou mais pedidos associados a essa Pessoa .

O modelo da faculdade também. Há muita coisa que pode e provavelmente deve ser compartilhada entre aluno e professor. Além disso, o que acontece quando você tem um professor em uma aula, como muitas vezes é permitido gratuitamente nos campi da faculdade?

Suponho que possa ser uma prática interessante, um elemento do kit de ferramentas de design. Eu não acho que deveria ser a única maneira de abordar o design, pelo menos. Francamente, acho a abordagem de análise de semelhança / variação mais útil. Parece-me modelar muito de perto o que fazemos na classificação de abstrações durante a vida cotidiana.

Edit: Basta ler metade desse segundo blog e devo dizer que concordo bastante. Vou ter que ler o resto e ver o que ele oferece em termos de aprendizado.

Edward Strange
fonte
2
Erro: Linha 2: hiperlink inválido!
Cracker
1
O software SE o manuseou. Estava funcionando bem na pré-visualização. Aqui está o link em forma de texto: objectmentor.com/resources/articles/CoffeeMaker.pdf
Edward Estranho
0

Minha opinião é que as classes devem ser adicionadas (e removidas) conforme você codifica para separar preocupações e reduzir dependências. Ser fluente em padrões de design é provavelmente uma boa aposta para ver possibilidades de refatoração e simplificação.

As aulas geralmente, na minha experiência, não se enquadram perfeitamente nas categorias de substantivos / verbos, mas você terminará com uma mistura de classes de substantivos / verbos junto com diferentes classes de padrões (fábricas, singletons, padrões de estratégia etc.) e outras classes de gerenciador que aborda um aspecto do seu aplicativo.

O principal é que seu objetivo seja poder olhar para uma classe e deduzir o que ela faz e modificá-la, alterando apenas essa classe. Quanto mais código para um aspecto do seu aplicativo estiver espalhado entre as classes, mais difícil será segui-lo, gerenciá-lo e estendê-lo.

Homde
fonte