it-swarm.it

Come gestisci il brutto codice che hai scritto?

Quindi il tuo cliente ti chiede di scrivere del codice, così fai. Quindi cambia le specifiche su di te, come previsto, e tu implementi diligentemente le sue nuove funzionalità come un bravo ragazzo. Tranne ... le nuove funzionalità sono in conflitto con le vecchie funzionalità, quindi ora il tuo codice è un casino. Tu davvero vuoi tornare indietro e aggiustarlo, ma continua a richiedere nuove cose e ogni volta che finisci di pulire qualcosa, finisce di nuovo un casino.

Cosa fai? Smetti di essere un maniaco del disturbo ossessivo compulsivo e accetti semplicemente che il tuo codice finirà per fare casino, qualunque cosa tu faccia, e continui a concentrarti sulle caratteristiche di questa mostruosità? Salvare la pulizia per la versione 2?

89
mpen

Trova un altro lavoro e consenti ad altre persone di affrontarlo. Muahahahhahahaa.

.....

Solo scherzando. :)

Ma in tutta serietà: riempimento di stima è tuo amico. In genere faccio una stima realistica decente, quindi la raddoppio. Questo può sembrare eccessivo, e talvolta lo è, ma è meglio sopravvalutare un po 'e persino sembrare un po' lento a volte - piuttosto che lasciare cattive impressioni rivelando il codice buggy e saltando sempre le tue stime. E, naturalmente, si incorre in un debito tecnico lasciando che il codebase diventi confuso.

Un altro suggerimento (correlato): stimare sempre attività apparentemente minuscole, senza sforzo in un blocco di dimensioni decenti. Supponiamo, ad esempio, che un elemento di cui sei quasi sicuro sarà solo un semplice cambio di 30 secondi di una riga: dagli 1 ora (o forse qualunque sia il periodo di tempo più basso sul tuo foglio presenze o sul tuo sistema CR, ad esempio 15 minuti/0,25 ore) . E dai blocchi di mezza giornata o 1 giorno per gli oggetti leggermente più grandi ma ancora relativamente banali.

La ragione di ciò è principalmente psicologica: trovo che se hai l'abitudine di fare rapidamente piccoli cambiamenti, il lavoro sembra affrettato, e non finisci mai per rilassarti, fare il punto e rifattorizzare le cose che devono essere rifattorizzate. Inoltre, a livello pratico: a volte esplodono piccoli ma non banali cambiamenti, e non vuoi sentirti costantemente come se fossi in ritardo e spegni bug. Fa parte del perché le basi di codice diventano confuse nel tempo.

Infine, ricorda sempre che le persone non devono sapere che stai riempiendo un po 'le tue stime. Finché sei uno sviluppatore competente e stai lavorando a un ritmo decente, questa imbottitura non sarà evidente. cioè non dire al PHB "La mia stima iniziale è che ci vorranno due ore, ma dammi mezza giornata". Digli semplicemente "Penso che ci vorrà circa mezza giornata." e lasciarlo lì.

41
Bobby Tables

Sopravvalutare deliberatamente il tempo necessario per le tue prossime funzionalità. Usa quel tempo in più per pulire.

Non sarai mai in grado di giustificare la manutenzione e il cliente ne avrà bisogno a prescindere, quindi dai loro la medicina amara (costi leggermente aumentati per le prossime funzionalità) in modo che possano migliorare.

66
Frank Shearar

Prova a riprogettare correttamente integrando nuove funzionalità. Non c'è più tardi. Senza la riprogettazione si aggiunge costantemente sempre più attrito per ulteriori modifiche e nuove funzionalità.

Ad un certo punto arriverete a una macinatura quasi ferma dove tutto sembra richiedere secoli. La maggior parte delle aziende probabilmente punta a una grande riscrittura a questo punto, versione 2. Ha un'economia piuttosto scadente ed è un buon momento per i tuoi clienti di provare un diverso partito di sviluppo se si sentono propensi.

Una corretta riprogettazione/refactoring può proteggere gli investimenti dei vostri clienti e mantenere le cose sostenibili. Devi integrarlo. Ottimizza per il cambiamento, viaggiare leggero.

11
Joppe

Con tutti i commenti sulla sopravvalutazione, penso che ci sia una modesta quantità di punti (ben opportunità) da perdere.

Non si tratta di stimare il tempo impiegato per apportare la modifica (solo) e quindi aggiungerne un po ', si tratta di stimare il tempo necessario per modificare il codice (refactor!) Per portarlo a un punto in cui la modifica può essere effettuata in modo sicuro e quindi effettuare il cambiamento (probabilmente un po 'insieme). Ok, questo equivale alla stessa cosa ... ma non si tratta di confondere o allungare o sopravvalutare, è semplicemente una questione di dire che per fare questo devo prima farlo e questo è quanto tempo ci vorrà in totale. La chiave qui è che lavori su quelle parti del sistema da cui dipende il cambiamento e non di più - se c'è un codice orribile altrove ... difficile, prendilo quando sei lì.

Per tornare un po 'alla domanda originale - dopo molti anni si riduce a questo per me, quando si implementa qualcosa a meno che sai (non credi, non ti aspetti (sospetto?), Non pensi ma sapere) che sono necessarie anche altre cose, allora dovresti fare quello che ti serve per implementare quel requisito e non più nel modo più ordinato ed elegante possibile.

Quando si arriva a implementare la cosa successiva - qualche tempo dopo - si prendono le misure necessarie per portare la base di codice (e il database e quant'altro) allo stato necessario per implementare quella funzionalità nel modo più ordinato ed elegante possibile. Questo refactoring è il punto in cui si affronta il disordine che si presenta naturalmente all'evolversi di un progetto e si spera di evitare di creare più disordine (o almeno mantenere il livello coerente).

Una delle aree di discussione qui è "Debito tecnico" - è come uno scoperto, devi rimborsarlo e più lo lasci, più interessi (in questo caso il tempo necessario per correggere) accumulerai - il che ti dà un buon argomento per passare un po 'del tuo tempo a minimizzare il debito tecnico.

Questo è anche il punto in cui iniziano i test unitari e altri test automatizzati (se potessi fare così come dico sono abbastanza sicuro che sarei una persona più felice!) In combinazione con un server di build adeguato (che può eseguire almeno alcuni dei tuoi test). Combinati con quelli - ma di valore in sé stessi - sono schemi come l'iniezione di dipendenza e l'inversione del controllo (mai abbastanza sicuri di quanto siano gli "stessi" quei due) perché rendono più facile cambiare l'impianto idraulico e quindi gestire i cambiamenti in isolamento.

Infine, ricorda, se non è rotto non aggiustarlo. Riordinare il codice esclusivamente per motivi di riordino può essere soddisfacente, ma è anche un'opportunità per introdurre errori, quindi può essere doloroso se non è necessario modificarlo e non ci si basa su di esso potrebbe essere meglio lasciare da soli alcuni grumi - alla fine la possibilità di riparare o sostituire andrà in giro!

6
Murph

1) Il controllo delle modifiche corretto è tuo amico

Se il cliente modifica le specifiche, va bene, è un suo diritto, tuttavia si tratta di una modifica e deve essere addebitata (o pagata in qualsiasi modo appropriato alla struttura/relazione del progetto).

La stima per quella modifica dovrebbe includere il costo del necessario refactoring. Il cliente potrebbe anche fare a meno di quello che sembra essere un costo elevato, ma a quel punto è necessario spiegargli che, poiché il codice è già scritto per metà, ci sono elementi che devono essere riscritti per garantire che sia solido e sostenibile in futuro e che se non viene fatto, è probabile che abbia problemi con il supporto futuro o che le modifiche diventino ancora più costose.

2) Il refactoring deve essere fatto in modo tale da fornire al cliente un vantaggio reale a lungo termine

Quando si considera il refactoring è sempre necessario considerare ciò che è effettivamente necessario e ciò che è importante e assicurarsi che il lavoro di refactoring offra un autentico valore a lungo termine.

Dopotutto, dovremmo fare queste cose in modo che il codice rimanga estendibile e sostenibile a medio/lungo termine per garantire che l'investimento del cliente rimanga valido piuttosto che fuori da ogni desiderio di perfezione teorica. Il lavoro di refactoring (e le stime corrispondenti) dovrebbe essere fatto con questo come scopo, e non solo perché ora pensi che potrebbe esserci un modo leggermente migliore per farlo.

4
Jon Hopkins

Alcuni programmatori suggeriscono che un modo per controllare quel problema con i client sia avere il segno del cliente e autorizzare la specifica iniziale. ALLORA, quando richiedono una modifica del requisito che non è nella specifica iniziale, si dice loro che è necessario passare attraverso il contratto e l'orario del progetto al fine di calcolare costi aggiuntivi e ritardi, quindi fare un allegato al contratto. Apparentemente fa miracoli nel impedire ai clienti di insistere su nuove funzionalità (non previste).

3
Jas

Ho il seguente commento in una base di codice su cui sto attualmente lavorando:

/*
 * Every time I see this function, I want to take a shower.
 */

Conosco molto bene la situazione che stai descrivendo. Quello che faccio è cercare (il mio meglio) di aspettare che le cose si stabilizzino e ogni tipo di "creep" ha "insinuato" tutto ciò che sta per fare. A quel punto, probabilmente hai rilasciato qualcosa di utilizzabile e puoi dedicare del tempo per ripulire le cose e implementare le cose in modo leggermente diverso.

Non puoi andare in giro a ripulire ripetutamente molti piccoli pasticci. Questo triplica il tuo lavoro e la tua frustrazione. Aspetta che diventi un disastro più grande, ma difficilmente commovente e quindi puoi fare qualcosa al riguardo.

3
Tim Post

La mia preferenza è quella di evitare questa situazione in primo luogo.

Tutto dipende da come leggi le specifiche. È facile pensarli come tavolette di pietra, ma in realtà la maggior parte delle specifiche cambia. Quando progetti il ​​tuo codice, dai un'occhiata alla probabilità che ogni parte delle specifiche cambi. Nel tempo, diventerai abbastanza bravo nel prevederlo.

Essere nel caos, esperienza e giudizio è molto importante. Stai scrivendo nuovi bug a causa di questo codice spaghetti? ci vuole più tempo per implementare? questi indicherebbero a fare un rifattore tattico.

per il futuro, sembra che tu debba lavorare in collaborazione con il tuo cliente. Dicendo loro, "guarda che questo prodotto si sta espandendo in modo significativo oltre le specifiche originali. Mentre il design originale era buono per quel livello, espandendolo in direzione X e direzioni Y hanno bisogno di una ristrutturazione nel design" gestito bene, e otterrai anche il tuo cliente a pagare per questo.

2
Michael Shaw

Addebita ogni ora e se vuole dei cambiamenti dì che va bene ma incorpora il tempo necessario per scrivere un buon codice nell'equazione. Ricorda anche che scrivere codice più ordinato paga a lungo termine quando devi mantenerlo. Risparmiare tempo ora potrebbe costarti in seguito.

2
Craig

Penso che la scrittura di software debba andare di pari passo con le esigenze aziendali. Se si tratta di un progetto usa e getta (come un prototipo che deve essere costruito in una settimana, con nuovi input in arrivo ogni giorno), non è necessario preoccuparsi della manutenibilità del codice e di altre cose: il tempo è cruciale e devi solo Spingi il codice fuori dalla porta il più velocemente possibile.

Ma se stai scrivendo un'app a lungo termine, ha senso considerare tutto questo, perché c'è un impatto considerevole su quanto tempo ci vuole per costruire nuove funzionalità, correggere bug esistenti, integrarsi in altre applicazioni e altre cose - e questo si traduce in impatto sul business (a causa di più tempo richiesto in seguito e più costi).

Quindi è meglio sensibilizzare il decisore ai costi effettivi di non refactoring del codice ogni volta che è necessario - nella mia esperienza, se i costi e l'impatto sul tempo di entrambe le opzioni sono spiegati in termini misurabili al proprietario della decisione, allora la decisione può essere un una follia. Non aspettarti che la gente ti dica "sì, vai avanti a scrivere un bellissimo codice, anche se ci vuole il doppio del tempo e non mi dà alcun vantaggio extra". Semplicemente non funziona in questo modo.

1
Roopesh Shenoy

Rendilo parte del tuo processo, lo chiamo "refactoring estremo" e sarà grande! ;) Basta fare le cose rapidamente e quando sono state aggiunte abbastanza nuove funzionalità che ci sono tessuto cicatriziale, refactor. Chiediti continuamente "Ora se avessi iniziato da zero, come avrei fatto"

Le persone che pensano di poter progettare e pensare a tutto ciò che è in anticipo si stanno prendendo in giro da sole, tu (e il tuo cliente) imparate sempre le cose mentre andate avanti. Usa quelle lezioni.

Dato che sei un buon programmatore, sarai in grado di eseguire il refactoring abbastanza rapidamente e man mano che lo fai, il codice inizierà a prendere la sua "forma corretta", il che significa che diventerà più flessibile con meno dipendenze.

I clienti potrebbero essere seccati se sapessero che stavi "perdendo tempo" a rielaborare le cose, quindi aiuta a non chiedere/raccontare ed essere molto veloce al riguardo.

Il codice sviluppato in questo modo ti farà risparmiare un sacco di tempo alla fine e renderà sempre più facile aggiungere nuove funzionalità.

Direi anche che uno dei maggiori motivi del cattivo codice è la paura che alcuni programmatori hanno di fare un refactoring strutturale più ampio, e più a lungo aspetti e peggio diventa.

1
Homde

Affidati a una potenza superiore

Non intendo pregare. Voglio dire, assicurati che ci sia un ragazzo d'affari (cioè project manager o equivalente) che puoi inserire come imbottitura tra te e il cliente. Se il cliente richiede troppo, lascia che l'uomo d'affari metta piede e sii pronto a esercitare il "è fattibile, ma non sono sicuro che si adatti allo scopo delle specifiche, vedi [uomo d'affari]".

In un normale flusso di progetto, le specifiche generali dovrebbero essere congelate prima che avvenga un serio sviluppo.

Molti clienti continueranno a guidare per cambiamenti/miglioramenti/miglioramenti fino a quando li lascerai. Molti abuseranno al massimo di questa capacità perché li fa sentire come se stessero ottenendo il massimo per i loro soldi (anche se sabota il tuo progetto).

Chiedi a una persona dedicata a perfezionare e congelare le specifiche all'inizio e farle rispettare in seguito.

Non c'è niente di sbagliato nel fare un piccolo extra per un po 'di buon karma con il cliente, ma sii pronto a rinviare a un potere superiore quando sfuggono di mano. Se la specifica richiede una quantità ridicola di modifiche, forse è il momento di tornare indietro nel ciclo economico e rivalutare il contratto e/o aggiungere aggiunte al contratto (con un equo compenso monetario).

Il fatto che stai riscontrando questo problema ha poco a che fare con il modo in cui il codice. È un segno che il tuo project manager è sottoutilizzato sul progetto (che sia colpa tua, colpa sua o entrambi).

Come altri hanno già detto in molte risposte, è necessario aggiungere un time buffer per le contingenze su qualsiasi progetto, ma determinare che dovrebbe essere deciso a porte chiuse prima che la specifica venga congelata e consegnata al cliente dal PM.

1
Evan Plaice

Risposta più semplice. Smetterei di scrivere codice di qualsiasi tipo, fino a quando non avrà una specifica finale per quello che vuole ora.

Quindi devono dare la priorità a quell'elenco di funzionalità ecc., Per confermare quali elementi devono avere adesso e quali possono essere fatti in seguito ...

Usando le tue esperienze per determinare quale sia il tempo/costo di ogni funzione, e poi dire loro, se lo vogliono, ci vorrà x quantità di tempo e denaro.

Stai affrontando il grande crimine dell'ambito delle funzionalità che si insinua e continueranno continuamente ad aggiungere funzionalità, fino a quando nulla viene mai fatto o fatto così male.

Dì loro una volta che avrai un elenco finale, che apporterai modifiche future, come preferiscono, ma devi concentrarti sui primi 15/20 che devono avere in questo momento.

Quindi, in base al tempo necessario per il completamento, digli che dopo che questo è stato rilasciato, sarai aperto a discutere/fare brainstorming sulla prossima versione.

Una volta presa la decisione finale su cosa fare per la versione attuale, tutte le discussioni/idee/suggerimenti devono essere fermati al 100%.

Se ottiene idee all'infinito, digli di scriverle, nel loro elenco di funzionalità per la versione successiva, e di concentrarti sulla fornitura delle funzionalità più importanti che desiderano in questo momento.

Se continuano a perdere tempo, continua a cambiare idea. Quindi smetterei di lavorare al progetto e di lavorare su altri progetti, fino a quando non avranno finalizzato le loro decisioni.

È difficile da fare, ma il creep di portata delle caratteristiche è così distruttivo di tempo, energia, motivazione e pensiero chiaro.

0
crosenblum

Dal punto di vista del progetto completo:

Impara dal codice con il tuo team, vedi cosa può essere refactored e riutilizzato la prossima volta, quindi vai a bere una birra.

Dal punto di vista dello sviluppo:

Spiega pazientemente perché lo sviluppo si è fermato e spiega perché non può continuare fino a quando tutte le specifiche sono sul tavolo e capite. Quindi vai a bere una birra.

Dal punto di vista della pianificazione:

Richiedi tutte le specifiche in anticipo e lavora con tutti per avere una chiara comprensione del percorso di sviluppo. Coinvolgi il cliente/le parti interessate il più vicino possibile per assicurarti che tutti siano sulla stessa pagina. Più tardi quella sera, prendi tutte le birre. Domani inizia il progetto.

0
Kevin

ccidilo con il fuoco.

Aka refactor il più presto possibile: ad esempio quando il codice brutto proviene dalla corsa per una scadenza, farei refactoring dopo la scadenza perché non puoi (o non dovresti almeno) aggiungere più funzionalità fino a quando il codice esistente non è mantenibile, altrimenti renderà molto più difficile il debug dei codici futuri.

0
wildpeaks

Una corretta progettazione iniziale non può aiutare a evitare il problema. Ed è quasi impossibile (o molto, molto difficile) considerare tutti i futuri requisiti "forse". Quindi dopo qualche tempo arriverà il Big Re-factoring. E la soluzione migliore è riscrivere tutto.

In poche parole: invece di montare una torretta sulla Ferrari rossa, riconsidera i requisiti e costruisci un serbatoio.

0
duros

Scrivi unit test per i tuoi progetti che testano lo stato corrente e poi refactoring quando hai tempo, in questo modo eviti di interrompere il tuo progetto mentre stai provando a ripulirlo.

0
chiurox