Como posso acertar as coisas no início de um projeto de software? [fechadas]

64

Sou programador com 1 ano de experiência, recentemente percebi que raramente inicio um projeto corretamente (a maioria do meu projeto paralelo), normalmente o ciclo do projeto é como

  1. Comece com alguns casos de uso
  2. Comece a codificar
  3. Perceba algumas coisas que não lidei bem e que não se encaixam bem na base de código atual.
  4. Reescreva a maior parte do código

e isso pode acontecer algumas vezes

Então, minhas perguntas são

  1. Essa prática é comum ou implica que eu não sou competente?
  2. Como posso me aprimorar nesse aspecto?
Qingwei
fonte
29
Perfeito! Isso é chamado de aprendizagem :) E competente = eficiente no dia 1!
6
Sua pergunta interessante é fora de tópico, pois parece um conselho de carreira. BTW também gostaria de sugerir a contribuir para algum projeto de software livre existente, você vai aprender muito (de uma comunidade de desenvolvedores, alguns deles sendo mais especialista do que você é hoje)
Basile Starynkevitch
6
Se você encontrar um método para iniciar cada projeto perfeitamente, informe-nos. Ou escreva um livro sobre isso e torne-se milionário.
Mast
11
@ Qingwei, você disse que começa com casos de uso, sem defini-los. Defini-los seria um tipo de análise, ie. dos requisitos do usuário. Eu acho que é melhor ter um entendimento mais completo e detalhado da maioria dos casos de uso desde o início. Quero dizer, encontrar apenas um novo caso de uso em um estágio posterior, geralmente pode significar retrabalho substancial. Melhor fazer o re-trabalho no design do que na implementação.
Brad Thomas
11
Acho que depende de quem você fala, mas os Casos de Uso da IMO são puramente requisitos. Eles devem ser escritos completamente desprovidos de quaisquer decisões de design. A análise inclui principalmente projetar / definir a arquitetura do sistema. Portanto, os Casos de Uso não pertencem como parte da Fase de Análise. Com isso dito, o que geralmente acontece é que você escreve alguns detalhes de casos de uso, atualiza os diagramas de arquitetura e itera de volta aos Casos de Uso para fazer as alterações identificadas ao fazer os diagramas de arquitetura e atualiza os diagramas com base nas alterações nos casos de uso . Então você continua iterando até ficar satisfeito com ambos.
Dunk

Respostas:

70

O ciclo que você descreve é ​​normal. A maneira de melhorar as coisas não é evitar esse ciclo, mas simplificá-lo. O primeiro passo é aceitar que:

  1. É quase impossível saber tudo no primeiro dia de um projeto.
  2. Mesmo que você saiba tudo de alguma forma, quando terminar o projeto, algo (os requisitos do cliente, o mercado em que está, a tecnologia com a qual você está trabalhando, os desejos dos clientes) terá mudado e produzido menos parte do que você sabia inválido ou incorreto.

Portanto, é impossível planejar tudo com antecedência, e mesmo que você pudesse, seguir esse plano levaria a criar algo imperfeito ou obsoleto. Sabendo disso, integramos as mudanças em nosso planejamento. Vejamos seus passos:

  1. Comece com alguns casos de uso
  2. Comece a codificar
  3. Perceba algumas coisas que não lidei bem e que não se encaixam bem na base de código atual.
  4. Reescreva a maior parte do código

Esse é realmente um ótimo ponto de partida. Aqui está como eu abordaria isso:

1. Comece com alguns casos de uso

Boa. Ao dizer "casos de uso", você está se concentrando no que o software é para . Ao dizer "alguns", você não está tentando descobrir tudo; você está mantendo uma quantidade gerenciável de trabalho. Tudo o que eu adicionaria aqui é priorizá-los. Com seu cliente ou usuário final, elabore a resposta para esta pergunta:

Qual é o software menor e mais simples que eu poderia fornecer para melhorar sua situação?

Este é o seu produto mínimo viável - qualquer coisa menor que isso não ajuda o usuário, mas qualquer coisa maior corre o risco de planejar muito cedo. Obtenha informações suficientes para criar isso e siga em frente. Lembre-se de que você não saberá tudo neste momento.

2. Comece a codificar.

Ótimo. Você começa a trabalhar o mais rápido possível. Até você escrever o código, seus clientes receberão zero benefício. Quanto mais tempo você gasta planejando, mais o cliente fica esperando sem retorno.

Aqui, eu adicionaria um lembrete para escrever um bom código. Lembre-se e siga os Princípios do SOLID , escreva testes de unidade decentes em torno de qualquer coisa frágil ou complexa, faça anotações sobre qualquer coisa que você provavelmente esqueça ou que possa causar problemas mais tarde. Você deseja estruturar seu código para que as alterações não causem problemas. Para fazer isso, toda vez que você decide criar algo dessa maneira, e não dessa maneira, estrutura seu código para que o mínimo de código possível seja afetado por essa decisão. Em geral, uma boa maneira de fazer isso é separar seu código:

  • use componentes simples e discretos (dependendo do idioma e da situação, esse componente pode ser uma função, uma classe, uma montagem, um módulo, um serviço etc. etc. Você também pode ter um componente grande construído com componentes menores, como uma classe com muitas funções ou uma montagem com muitas classes.)
  • cada componente faz um trabalho ou trabalhos relacionados a uma coisa
  • mudanças na maneira como um componente faz seu funcionamento interno não deve fazer com que outros componentes precisem mudar
  • componentes devem receber itens de que usam ou dependem, em vez de buscá - los ou criá- los
  • componentes devem fornecer informações a outros componentes e pedir que eles façam o trabalho, em vez de buscar informações e fazer o trabalho por si mesmos
  • componentes não devem acessar, usar ou depender do funcionamento interno de outros componentes - use apenas suas funções acessíveis ao público

Ao fazer isso, você está isolando os efeitos de uma alteração para que, na maioria dos casos, possa corrigir um problema em um só lugar, e o restante do seu código não perceba.

3. Problemas ou deficiências no projeto.

Isso vai acontecer. É inevitável. Aceite isso. Quando você encontrar um desses problemas, decida que tipo de problema é esse.

Alguns problemas são problemas no seu código ou design que dificultam o que o software deve fazer. Para esses problemas, você precisa voltar e alterar seu design para corrigir o problema.

Alguns problemas são causados ​​por não ter informações suficientes ou por algo que você não pensava antes. Para esses problemas, é necessário voltar ao usuário ou cliente e perguntar como eles gostariam de resolver o problema. Quando você tiver a resposta, atualize seu design para lidar com isso.

Nos dois casos, você deve prestar atenção em quais partes do seu código tiveram que ser alteradas e, à medida que escreve mais código, deve pensar em quais partes devem ser alteradas no futuro. Isso torna mais fácil descobrir quais partes podem estar muito interligadas e quais partes precisam ser mais isoladas.

4. Reescreva parte do código

Depois de identificar como você precisa alterar o código, você pode fazer a alteração. Se você estruturou bem o seu código, isso normalmente envolverá a alteração de apenas um componente, mas em alguns casos, poderá incluir a adição de alguns componentes. Se você achar que precisa mudar muitas coisas em muitos lugares, pense no motivo disso. Você poderia adicionar um componente que mantém todo esse código dentro de si e, em seguida, ter todos esses locais apenas usando esse componente? Se você puder, faça isso e, da próxima vez que precisar alterar esse recurso, poderá fazê-lo em um só lugar.

5. Teste

Uma causa comum de problemas no software é não conhecer os requisitos suficientemente bem. Isso geralmente não é culpa dos desenvolvedores - muitas vezes, o usuário também não tem certeza do que precisa. A maneira mais fácil de resolver isso é reverter a questão. Em vez de perguntar "o que você precisa que o software faça?", Cada vez que você seguir essas etapas, dê ao usuário o que você criou até agora e pergunte a ele "Eu criei isso - ele faz o que você precisa?". Se eles disserem que sim, então você criou algo que resolve o problema deles e pode parar de trabalhar! Se eles recusarem, poderão dizer em termos mais específicos o que há de errado com o seu software, e você poderá melhorar essa coisa específica e voltar para obter mais comentários.

6. Aprenda

À medida que você passa por esse ciclo, preste atenção nos problemas que está encontrando e nas mudanças que está fazendo. Existem padrões? Você pode melhorar?

Alguns exemplos:

  • Se você continuar ignorando o ponto de vista de um determinado usuário, poderá fazer com que esse usuário se envolva mais na fase de design?
  • Se você continuar tendo que mudar as coisas para ser compatível com uma tecnologia, poderá criar algo para fazer a interface entre seu código e essa tecnologia, para ter apenas que mudar a interface?
  • Se o usuário continuar mudando de idéia sobre palavras, cores, imagens ou outras coisas na interface do usuário, você poderá criar um componente que forneça ao restante do aplicativo aqueles para que eles estejam todos no mesmo local?
  • Se você achar que muitas das alterações estão no mesmo componente, tem certeza de que o componente está aderindo a apenas um trabalho? Você poderia dividi-lo em alguns pedaços menores? Você pode alterar esse componente sem precisar tocar em outros?

Seja ágil

O que você está seguindo aqui é um estilo de trabalho conhecido como Agile. Agile não é uma metodologia, é uma família de metodologias que incorpora um monte de coisas (Scrum, XP, Kanban, para citar algumas), mas o que todos eles têm em comum é a ideia de que as coisas mudam e, como desenvolvedores de software, deve planejar se adaptar às mudanças em vez de evitá-las ou ignorá-las. Alguns de seus princípios básicos - em particular os que são relevantes para sua situação - são os seguintes:

  • Não planeje com mais antecedência do que você pode prever com confiança
  • Faça concessões para que as coisas mudem à medida que avança
  • Em vez de criar algo grande de uma só vez, crie algo pequeno e aprimore-o gradualmente
  • Mantenha o usuário final envolvido no processo e obtenha feedback rápido e regular
  • Examine seu próprio trabalho e progresso e aprenda com seus erros
anaximander
fonte
5
"Ótimo. Você começa a trabalhar o mais rápido possível. Até você escrever o código, seus clientes receberão zero benefício. Quanto mais tempo você gasta planejando, mais tempo o cliente fica esperando, sem retorno." Não posso concordar com isso de forma alguma. Quanto menos tempo você gasta planejando, mais o cliente gasta esperando por algo que realmente funcione corretamente, sem retorno.
Lightness Races com Monica
4
@ RobCrawford: Existe todo um continuum entre "sem planejamento" e "planejamento excessivo". O "planejamento" ou "visão" acima exposto provavelmente fará com que você corra ... em círculos. Agile não é sobre "não planejar", é sobre evitar confiar em elementos incertos e ser capaz de mudar as metas à medida que você avança: você ainda precisa de algum tipo de meta abrangente, mesmo que seja embaçada / imprecisa, caso contrário você não pode medir se o que você desenvolve é progresso ou saída.
Matthieu M.
7
Acho que todos vocês que se opõem à "falta de planejamento" ignoraram completamente o fato de que o primeiro passo é identificar o produto mínimo viável. Isso necessariamente implica algum planejamento. Parece-me que o objetivo deste post é mais desencorajar a tentativa de obter um design perfeito na frente; em vez disso, planeje e não gaste para sempre tentando identificar tudo com antecedência.
Jpmc26 06/07/19
3
Uau, então isso explodiu. Como observaram os comentaristas, NÃO advogo o planejamento zero. O que estou dizendo - e o que o Agile diz - é não fazer muito planejamento. Digo explicitamente: "Não planeje com mais antecedência do que você pode prever com confiança". As pessoas que dizem que eu defendo o "mergulho direto na codificação" devem observar que a codificação é a etapa 2, onde a etapa 1 é ... bem, o planejamento . O truque é fazer um planejamento suficiente para determinar o menor produto que ajuda o usuário e , em seguida, fornecer esse produto .
Anaximandro
3
Para concluir, o Agile concorda que existe pouco planejamento. Apenas sugere que também existe algo demais.
Anaximander 06/07/19
14

Isto é normal.

Você pode adotar uma das duas abordagens:

  1. Welcome Change

Se você presumir que errou, deverá criar uma base de código aberta a alterações. Principalmente, isso envolve pegar o código no final de um livro sobre refatoração e criar seu código dessa maneira desde o início (decomposição, boa cobertura de teste, ...).

  1. Evitar mudanças

Nesse caso, você deve fazer um BDUF (design grande na frente). Você precisa fazer muita prototipagem de papel, discutindo idéias com usuários em potencial ou você mesmo, esquivando-se, testando várias coisas em protótipos ou modelos, anotando uma especificação completa e somente quando sentir que acertou a solução e finalmente finalmente pode começar a codificar. Fazendo tudo o que realmente não se livra de mudanças inesperadas, apenas reduz um pouco, o primeiro ano ou mais. Portanto, você ainda precisa criar seu código para facilitar a alteração.

Então, basicamente, a mudança é um dado. Suponha que isso aconteça. Crie seu código adequadamente. Na prática, você pode encontrar um meio termo entre as abordagens de design inicial e de codificação apenas inicial, que evitam mudanças gratuitas sem ficarem paralisadas na paralisia da análise. É preciso apenas um pouco de experiência.

Joeri Sebrechts
fonte
11

O desenvolvimento de software foi descrito como uma série de problemas inerentemente "perversos" .

Horst Rittel e Melvin Webber definiram um problema "perverso" como um problema que poderia ser claramente definido apenas por resolvê-lo ou resolver parte dele *. Esse paradoxo implica, essencialmente, que você precisa "resolver" o problema uma vez para defini-lo claramente e depois resolvê-lo novamente para criar uma solução que funcione. Esse processo tem sido maternidade e torta de maçã no desenvolvimento de software há décadas

Isso descreve perfeitamente o problema que você está enfrentando. Fundamentalmente, o que fazemos é difícil . Se houver uma parte que possa ser descrita como "rotina", com o tempo, nós a isolamos e automatizamos. Então, tudo o que resta é o novo ou o difícil.

Existem outras maneiras de superar problemas como esse; algumas pessoas passam muito tempo considerando os problemas com antecedência e não escrevendo código até se sentirem confortáveis ​​com o design. Outros buscam orientação de pessoas que já lidaram com problemas como esse, por meio de programação em pares ou apenas sites como esse.

Mas certamente sua abordagem não sugere incompetência. O único problema pode ser se, quando você voltar novamente, não estiver refletindo sobre o motivo de ter optado por fazer as coisas dessa maneira, e se poderá ver o caminho "melhor" sem o reescrever.

Em muitos casos, houve, e você pode incorporá-lo ao seu processo de design para a próxima vez. Em alguns casos, não havia (ou o custo teria sido tão alto ou mais alto que o custo de sua outra abordagem), e você pode simplesmente deixar sua preocupação ir.

Deworde
fonte
8
  1. Sim, isso é comum, exceto talvez pela parte "reescreva a maior parte do código". Você nunca receberá todos os requisitos desde o início, por isso é importante lidar bem com as mudanças. É disso que trata o conceito de "manutenção de código". Obviamente, também ajuda a dedicar mais tempo a obter os requisitos e o design corretos.
  2. Primeiro, pense em quais mudanças foram necessárias em projetos anteriores e como você poderia tê-las previsto ou preparado para eles melhor. No início de um projeto, pense mais nos detalhes dos casos de uso. Faça um design abstrato (quais são os principais componentes do código e como eles se comunicam, quais são suas APIs) antes de começar a implementar. Mais importante, tente manter o código o mais simples e fácil de alterar possível, leia conceitos como SOLID, DRY, KISS e YAGNI.
Michael Borgwardt
fonte
6

Essa prática é comum ou implica que eu não sou competente?

Esses não são mutuamente exclusivos. O padrão pode ser comum e você ainda pode ser incompetente. Sua competência pode ser determinada medindo seu desempenho em relação aos seus objetivos. Você está alcançando seus objetivos?

Esse padrão é comum? Infelizmente sim. Muitas pessoas mergulham em projetos sem uma idéia clara de qual problema estão solucionando, como projetarão uma solução correta e quais métricas constituirão sucesso.

Como posso me aprimorar nesse aspecto?

Se você decidiu ir a algum lugar e começou a andar, e descobriu um dia em que realmente precisava transportar um elefante da Cidade do Cabo para Nova York, todo o tempo que passava andando era desperdiçado. Descubra o que você está fazendo antes de começar.

Depois de começar, considere: como é o código que não precisa ser reescrito ? Esse código:

  • Faz uma coisa útil.
  • Faz corretamente.
  • Faz isso com desempenho suficiente.

Portanto: quanto mais código você escreve, em que esse código faz uma coisa útil, corretamente, com bom desempenho, menos código você precisará reescrever.

Eric Lippert
fonte
1

Eu acho que é seguro dizer que você não está tão longe de uma maneira melhor de trabalhar, e você não é o único neste barco.

O que eu acho que está faltando é que, embora a determinar o que você quer, você não parar de fazer o mesmo processo para como você vai fazer isso.

Essa etapa de parar e pensar em como lidar com o problema geral é chamada de design; é a etapa que faz com que você gaste algum tempo no desenvolvimento da estrutura ou arquitetura do sistema, para que tudo o que você faça a partir deles contribua para a solução final, como encaixar peças em um quebra-cabeça depois de trabalhar as bordas.

Muitas pessoas não fazem essa etapa, mas quando eu comecei a codificar era obrigatório. Eu acho que a diferença está nas ferramentas de desenvolvimento - enquanto eu comecei com um editor de texto, agora você tem todos os tipos de recursos que permitem entrar e digitar.

Portanto, reserve um tempo para descobrir as amplas áreas, componentes e interoperabilidade entre eles, e defina os objetos que farão parte da sua solução antes de começar a codificar. Ele não precisa ter muitos detalhes e entender que você não vai acertar perfeitamente no início, então evoluirá com o tempo, mas o que isso faz é ajudar a impedir que você desperdice seu esforço de revisar as coisas que não deveriam ' Não precisa mudar muito.

gbjbaanb
fonte
1

Você já tem ótimas respostas, mas sua pergunta me lembra algumas coisas que eu pensei em tentar abordar.

  1. Como você observou, enfrentando mudanças no caminho, sugiro pensar em como as coisas impactaram seu projeto e como você poderia ter minimizado o impacto com as opções de design / codificação, ao mesmo tempo em que gerava um mapa mental de onde as pessoas costumam fazer alterações tardias. Com a experiência, você pode antecipar e codificar com alguma flexibilidade as coisas que você sabe que serão importantes - embora exista um desacordo sobre esse conceito no setor, pois alguns irão contra-atacar o investimento de esforços em uma área não solicitada especificamente, por si só .

  2. Na frente dos testes, lançar um protótipo para as partes interessadas do projeto pode ser uma ótima maneira de refinar os requisitos. No entanto, durante o desenvolvimento, você pode procurar maneiras de "ver" o que está acontecendo no seu código sem causar muita confusão ou complexidade. Certamente existem ferramentas disponíveis para ajudar, mas você também pode fazer muito sem elas, se quiser. De qualquer forma, sair do código para examinar o que está acontecendo com um olhar crítico pode fornecer vários tipos de informações.

  3. Procure atividades comuns. Você se encontrará lidando com os mesmos problemas repetidamente. Depois de um tempo, você deve descobrir as deficiências ou compensações de várias opções e se concentrar em uma metodologia que o ajude a evitá-las. Obviamente, se você estiver trabalhando em uma estrutura, alguns desses problemas podem estar envolvidos nas ferramentas que você já está usando.

  4. Se você estiver trabalhando em uma estrutura, gaste o tempo, se puder poupá-la, para considerar como fazer as coisas do zero. Por exemplo, você pode montar facilmente uma mensagem de solicitação, abrir um soquete e emitir uma solicitação GET ou POST manualmente. Se desejar, você pode analisar manualmente as mensagens XML. Faça o que fizer, as perguntas que você gerar e as respostas que encontrar aumentam suas habilidades. Obviamente, você pode escolher quais tipos de questões subjacentes são importantes ou de interesse. Eu consideraria esse desenvolvimento pessoal e não esperaria gastar muito tempo aqui.

  5. Balas de prata, metodologias e questões de alto fator de zumbido estão por toda parte. Basicamente, as realidades subjacentes ao trabalho com informações não estão mudando tão rapidamente. Observe se a estrutura, o conjunto de ferramentas ou a metodologia em vigor é uma ajuda ou um obstáculo em várias situações. Nas grandes empresas, vi muitas metodologias tentadas, embora a empresa não tenha conseguido executá-las efetivamente. Assim como as estruturas, as metodologias não são uma maneira segura de funcionar em alto nível, mesmo se forem baseadas nas práticas de algumas equipes altamente funcionais.

É difícil resumir a experiência e tê-la acessível. Acho que uma maneira curta de colocar tudo isso é manter os olhos abertos, pensar no que vê e nunca parar de aprender.

Max Haaksman
fonte
1

Eu gostaria de adicionar alguns ponteiros

1) Pessoalmente, achei incrivelmente útil começar visualizando coisas. Desenhe caixas, setas, linhas ... Não importa a linguagem de modelagem usada. Em primeiro lugar, você está fazendo isso POR SI MESMO. Deve ajudar o seu fluxo de pensamentos.

2) Encontre um parceiro de treino - pegue um café e o flipchart / diagrama etc. acima e vá para a cidade. IMHO é ainda melhor se você não tiver habilidades técnicas correspondentes. Você alterna entre as idéias para implementar o caso de uso. Você encontra um beco sem saída ou dois - você encontra uma solução. Com uma mente ágil, muitas vezes há menos tempo gasto nesse estágio do que se você escrever código, ele não funcionará e você terá que eliminar partes do seu trabalho ou refazê-las.

3) Encontre um chefe que possa entender que você provavelmente nunca terminou de melhorar seu software escrito. Se você sempre conecta novos recursos / requisitos que são descartados em sua mesa e nunca se importa com o seu software, ele irá atacar você com bugs, hostilidade na manutenção e muitos cabelos puxando alguns anos na linha. Obtenha esse tempo / orçamento de manutenção de software alocado! Um bom número mágico redondo é cerca de 20% do tempo necessário para desenvolver o software por ano para mantê-lo em forma durante o curso de sua vida útil.

4) Esse processo de aprendizado incremental nunca para (e não deveria)! Você vai olhar para trás em 10 anos e sorrir.

Espero que isso ajude um pouco e boa sorte!

Christian Meißler
fonte
Deve ler "tanto faz". Editou a postagem acima.
Christian Meißler 07/07
Ótimas recomendações!
Dan