Quando è meglio ottimizzare un software per prestazioni migliori, all'inizio o alla fine dello sviluppo?


19

Sono uno sviluppatore di software junior e mi chiedevo quando sarebbe il momento migliore per ottimizzare un software per prestazioni migliori (velocità).

Supponendo che il software non sia estremamente grande e complesso da gestire, è meglio dedicare più tempo all'inizio all'ottimizzazione o dovrei semplicemente sviluppare il software che esegue correttamente tutte le funzionalità e quindi procedere all'ottimizzazione per prestazioni migliori?


7
Esperimento di pensiero: scegli un linguaggio di programmazione interpretato per sviluppare il tuo gioco interattivo e scopri a metà del processo di sviluppo che il linguaggio che hai scelto non possiede la velocità necessaria per soddisfare il tuo requisito di frame rate. Sei fregato in modo regale?
Robert Harvey,

8
Un altro esperimento mentale: ottimizzi attentamente un codice nel tuo gioco che ritieni fondamentale per le prestazioni, ma poi esegui un profiler sul codice e scopri che il codice che hai ottimizzato non contribuisce in modo significativo alle prestazioni complessive, e hai diminuito la chiarezza del codice. Hai perso tempo?
Robert Harvey,

8
Corollario: è una o / o una decisione, o potrebbe essere importante prendere alcune decisioni sulla performance all'inizio, rinviandone altre?
Robert Harvey,

1
Stavo scrivendo ed eliminando una risposta e continuavo a riscriverla. Non c'è una sola risposta a questa domanda perché dipende. In alcuni casi accelerare un prodotto supera tutte le altre considerazioni, in altri casi l'ottimizzazione dall'inizio è un requisito difficile e un milione di altri scenari in cui è valido o non ottimizzare, ottimizzare dall'inizio o non ottimizzare affatto e qualsiasi altra cosa.
Pieter B,

Non importa come lo guardi. All'inizio non c'è nulla da ottimizzare poiché non c'è nulla da confrontare. Hai ancora bisogno di 2 riferimenti per ottimizzare qualcosa: la prestazione ideale (in base ai requisiti) e quella reale (quella che ottieni una volta che hai fatto funzionare qualcosa).
Laiv

Risposte:


52

La cosa numero uno dovrebbe essere sempre e per sempre leggibilità. Se è lento ma leggibile, posso ripararlo. Se è rotto ma leggibile, posso ripararlo. Se è illeggibile, devo chiedere a qualcun altro cosa avrebbe dovuto fare.

È notevole quanto possa essere performante il tuo codice quando eri concentrato solo sulla lettura. Tanto che generalmente ignoro le prestazioni fino a quando non mi viene dato un motivo per preoccuparmi. Ciò non dovrebbe essere inteso nel senso che non mi interessa la velocità. Lo voglio. Ho appena scoperto che ci sono pochissimi problemi le cui soluzioni in realtà sono più veloci se rese difficili da leggere.

Solo due cose mi portano fuori da questa modalità:

  1. Quando vedo la possibilità di un grande miglioramento in piena regola , anche allora solo quando n è abbastanza grande da interessarsene.
  2. Quando ho dei test che mostrano problemi di prestazioni reali. Anche con decenni di esperienza, mi fido ancora dei test più della mia matematica. E sono bravo in matematica.

In ogni caso, evita la paralisi dell'analisi facendoti pensare che non dovresti provare una soluzione perché potrebbe non essere la più veloce. Il tuo codice trarrà effettivamente vantaggio se provi più soluzioni perché apportare le modifiche ti costringerà a utilizzare un design che lo rende facile da modificare. Una base di codice flessibile può essere resa più veloce in seguito dove ne ha davvero bisogno. Scegli flessibile sulla velocità e puoi scegliere la velocità di cui hai bisogno.


Ho sempre scoperto che la cosa principale su cui gli sviluppatori di software dovrebbero concentrarsi è ottenere un prodotto sugli scaffali il più velocemente possibile con un'interfaccia quanto più carina possibile, i bug e la cattiva progettazione possono essere risolti in seguito.
Pieter B,

12
@PieterB: è straordinariamente facile rallentare lo sviluppo con una strategia come "bug e cattiva progettazione possono essere risolti in seguito" . Si noti che per cattiva progettazione intendo cose come codice illeggibile, contorto, nonché codice troppo ingegnerizzato.
Doc Brown

5
@Walfrat: penso che il tuo esempio possa essere facilmente accelerato senza sacrificare la leggibilità, e sto interpretando questa risposta non come "il codice leggibile non ha alcun problema di prestazioni", ma più come "i problemi di perfomance non saranno automaticamente evitati facendo il codice illeggibile".
Doc Brown

2
@PieterB: o hai un cliente che vuole riavere i suoi soldi perché il prodotto che hanno comprato è così pieno che non possono usarlo.
Doc Brown

2
@svidgen valutare la velocità del codice illeggibile senza test è quasi impossibile. Concentrarsi sulla velocità e ignorare la leggibilità crea problemi di velocità non riconoscibili. Concentrarsi sulla leggibilità rende i problemi di velocità così ovvi che non dovrai pensarci. Lo vedrai nel momento in cui lo scrivi. Anche se non lo fai, una volta testato almeno sarai in grado di trovare il problema. Alla luce di tutto ciò, perché chiunque dovrebbe concentrarsi sulla velocità sulla leggibilità? Concentrarsi sulla velocità e ignorare la leggibilità non ti dà nessuno dei due.
candied_orange

27

Se è necessario un certo livello di prestazioni (un requisito non funzionale), questo dovrebbe essere un obiettivo di progettazione sin dall'inizio. Ad esempio, ciò può influenzare quali tecnologie potrebbero essere appropriate o come strutturare il flusso di dati nel programma.

Ma in generale, non è possibile ottimizzare prima che il codice sia scritto: prima farlo funzionare, quindi farlo bene e, infine, farlo velocemente .

Un grosso problema con l'ottimizzazione prima di implementare la maggior parte delle funzionalità è che ti sei bloccato in decisioni di progettazione non ottimali nei punti sbagliati. C'è spesso (ma non necessariamente) un compromesso tra manutenibilità e prestazioni. La maggior parte delle parti del programma sono totalmente irrilevanti per le prestazioni! I programmi tipici hanno solo alcuni hot spot che vale davvero la pena ottimizzare. Quindi sacrificare la manutenibilità per le prestazioni in tutti quei luoghi che non necessitano di prestazioni è un vero affare.

L'ottimizzazione per la manutenibilità è l'approccio migliore. Se spendi la tua intelligenza in manutenibilità e progetti chiari, a lungo termine sarà più facile identificare sezioni critiche e ottimizzarle in sicurezza senza compromettere la progettazione complessiva.


15

quando sarebbe il momento migliore per ottimizzare un software per prestazioni migliori (velocità).

Inizia rimuovendo dalla tua mente il concetto che le prestazioni sono la stessa cosa della velocità. Le prestazioni sono ciò che l'utente ritiene siano le prestazioni .

Se fai in modo che un'applicazione risponda due volte più velocemente a un clic del mouse e passi da dieci microsecondi a cinque microsecondi, l'utente non se ne preoccupa. Se fai in modo che un'applicazione risponda due volte più velocemente a un clic del mouse e passi da quattromila a duemila anni, di nuovo, l'utente non se ne preoccupa.

Se si effettua l'applicazione due volte più velocemente e si esaurisce tutta la memoria della macchina e si arresta in modo anomalo, all'utente non importa che sia due volte più veloce.

Le prestazioni sono la scienza per creare compromessi efficaci sul consumo di risorse per ottenere una particolare esperienza utente. Il tempo dell'utente è una risorsa importante , ma non è mai solo "più veloce". Il raggiungimento di obiettivi prestazionali richiede quasi sempre compromessi e spesso vengono scambiati fuori tempo per lo spazio o viceversa.

Supponendo che il software non sia estremamente grande e complesso da gestire

È un presupposto terribile.

Se il software non è grande e complesso da gestire, probabilmente non risolve un problema interessante che interessa a un utente ed è probabilmente super facile da ottimizzare.

è meglio dedicare più tempo all'inizio all'ottimizzazione o devo semplicemente sviluppare il software che esegue correttamente tutte le funzionalità e quindi procedere all'ottimizzazione per prestazioni migliori?

Sei seduto lì a una pagina vuota e scrivi void main() {}Inizia a ottimizzare? Non c'è niente da ottimizzare! L'ordine giusto è:

  • Fallo compilare
  • Rendilo corretto
  • Rendilo elegante
  • Fallo veloce

Se provi a farlo in qualsiasi altro ordine, finisci con un codice errato che è un disastro, e ora hai un programma che produce risposte sbagliate molto rapidamente e resiste alle modifiche.

Ma c'è un passo mancante lì. Il vero ordine giusto è:

  • Collabora con i clienti e il management per stabilire metriche e obiettivi di performance realistici e misurabili, ricordando che la velocità non è l'unica metrica a cui i clienti tengono.
  • Implementa un cablaggio di prova in grado di tracciare lo stato corrente del progetto rispetto ai tuoi obiettivi
  • Fallo compilare
  • Esegui i test. Se non sei più all'interno del tuo obiettivo, renditi conto che potresti aver preso una brutta strada in anticipo. Usa la scienza . Hai introdotto un cattivo algoritmo che può essere risolto o qualcosa di fondamentalmente sbagliato? Se è fondamentalmente sbagliato, ricominciare da capo. Se può essere risolto, inserisci un bug e tornaci più tardi.
  • Rendilo corretto
  • Esegui di nuovo i test ...
  • Rendilo elegante
  • Esegui di nuovo i test ...
  • Sei conforme al tuo obiettivo? Se sì, vai in spiaggia . In caso contrario, rendilo abbastanza veloce .

"Le prestazioni sono ciò che l'utente ritiene siano le prestazioni." - anzi, a volte l'esperienza dell'utente è in realtà meglio quando le cose ci si aspetta di prendere tempo fanno prendere tempo: webdesignerdepot.com/2017/09/when-slower-ux-is-better-ux
svidgen

forse "sii scientifico" piuttosto che "usa la scienza" :)
blu

@svidgen: ricordo di aver cambiato una volta il mio codice per rallentare una barra di avanzamento. Gli utenti hanno avuto l'impressione che fosse in corso un vero lavoro e ne erano contenti. La funzione da calcolare era utile ma sembrava che il programma non stesse facendo nulla se il risultato fosse stato lì dopo un decimo di secondo.
Giorgio,

2
@Giorgio: Questo mi risale, ma ricordo quando ho avuto un disco rigido per la prima volta, e avrei salvato un gioco o un documento e pensavo che qualcosa fosse andato storto perché l'operazione non richiedeva tempo percettibile rispetto al salvataggio su floppy disk. E ovviamente ora lo stato del gioco e i documenti sono così grandi che siamo tornati a risparmiare tempo.
Eric Lippert,

3

Come regola generale, è meglio ottimizzare le prestazioni in un secondo momento, ma ho visto molti progetti andare male quando gli sviluppatori si rendono conto di aver finito con un software che rallenta quando vengono aggiunti dati o carichi significativi.

Quindi, secondo me sarebbe meglio un approccio di medio livello; non porre troppa enfasi su di esso, ma non trascurare del tutto le prestazioni.

Farò un esempio che ho visto molte volte; data una libreria ORM, abbiamo un'entità Utente che può avere uno o più Ordini. Facciamo un ciclo di tutti gli ordini per un utente e scopriamo quanto l'utente ha speso nel nostro negozio - un approccio ingenuo:

User user = getUser();
int totalAmount;
for (Order o : user.getOrders()) {
  totalAmount += o.getTotalAmount();
} 

Ho visto gli sviluppatori scrivere cose simili, senza pensare alle implicazioni; prima otteniamo l'utente, che si spera sarà solo una query SQL nella tabella Utente (ma potrebbe comportare molto, molto di più), quindi eseguiamo il ciclo degli ordini, che potrebbe includere la ricezione di tutti i dati rilevanti per tutte le righe dell'ordine sull'ordine , informazioni sul prodotto, ecc. - tutto questo solo per ottenere un singolo numero intero per ogni ordine!

La quantità di query SQL qui potrebbe sorprenderti. Naturalmente, dipende da come sono strutturate le entità.

Qui, l'approccio corretto sarebbe molto probabilmente quello di aggiungere una funzione separata per ottenere la somma dal database tramite una query separata scritta nel linguaggio di query fornito dall'ORM, e raccomanderei di farlo la prima volta e non rimandare questo per dopo; perché se lo fai, probabilmente finirai con molti più problemi di cui occuparti, e non sei sicuro da dove cominciare.


3

Le prestazioni totali del sistema sono un prodotto delle interazioni complesse della totalità dei componenti del sistema. È un sistema non lineare. Pertanto le prestazioni non saranno solo correlate alle prestazioni individuali dei componenti, ma anche dai colli di bottiglia tra di loro.

Ovviamente non puoi testare i colli di bottiglia se tutti i componenti del tuo sistema non sono ancora stati creati, quindi non puoi davvero testare molto bene all'inizio. D'altra parte, dopo che il sistema è stato creato, potrebbe non essere facile apportare le modifiche necessarie per ottenere le prestazioni desiderate. Quindi questo è un fide - osseo Catch-22 .

Per rendere le cose più difficili, il profilo delle prestazioni può cambiare drasticamente quando si passa a un ambiente simile alla produzione, che spesso non è disponibile all'inizio.

Allora cosa fai? Bene, alcune cose.

  1. Sii pragmatico. All'inizio, puoi scegliere di utilizzare le funzionalità della piattaforma che sono "best practice" per le prestazioni; ad esempio, utilizzare il pool di connessioni, le transazioni asincrone ed evitare lo stato, che può essere la morte di un'applicazione multi-thread in cui diversi lavoratori si contendono l'accesso ai dati condivisi. Normalmente non testeresti questi schemi per le prestazioni, sapresti per esperienza cosa funziona bene.

  2. Sii iterativo. Adottare misure prestazionali di base quando il sistema è relativamente nuovo e testare di tanto in tanto per assicurarsi che il codice appena introdotto non abbia degradato troppo le prestazioni.

  3. Non ottimizzare troppo presto. Non si sa mai cosa sarà importante e cosa non avrà importanza; un algoritmo di analisi delle stringhe superveloce potrebbe non essere utile se, ad esempio, il programma è costantemente in attesa di I / O.

  4. Soprattutto nelle applicazioni Web, puoi concentrarti non tanto sulle prestazioni ma sulla scalabilità. Se l'applicazione può ridimensionarsi, le prestazioni non contano, dal momento che è possibile continuare ad aggiungere nodi alla farm fino a quando non è abbastanza veloce.

  5. Particolare attenzione va al database. A causa di vincoli di integrità transazionale, il database tende ad essere un collo di bottiglia che domina ogni parte del sistema. Se hai bisogno di un sistema ad alte prestazioni, assicurati di avere persone di talento che lavorano sul lato database, riesaminando i piani di query e sviluppando strutture di tabelle e indici che renderanno le operazioni comuni il più efficienti possibile.

La maggior parte di queste attività non riguarda l'inizio o la fine del progetto, ma deve essere seguita continuamente .


1

Sono uno sviluppatore di software junior e mi chiedevo quando sarebbe il momento migliore per ottimizzare un software per prestazioni migliori (velocità).

Comprendi che ci sono 2 estremi molto diversi.

Il primo estremo sono le cose che influenzano gran parte del design, come come suddividere il lavoro in quanti processi e / o thread e in che modo i pezzi comunicano (socket TCP / IP? Chiamate di funzione dirette?), Se implementare un JIT avanzato o un interprete "un codice operativo alla volta", o se pianificare strutture dati che possono essere rese disponibili per SIMD, o ... Queste cose tendono ad avere una forte influenza sull'implementazione e diventano eccessivamente difficili / costose da adattarsi dopo.

L'altro estremo è la microottimizzazione: piccole piccole modifiche dappertutto. Queste cose tendono a non avere quasi alcuna influenza sull'implementazione (e spesso sono comunque meglio eseguite da un compilatore), ed è banale fare queste ottimizzazioni ogni volta che ne hai voglia.

Tra questi due estremi c'è un'enorme area grigia.

Ciò che si riduce davvero è l'esperienza / ipotesi istruite utilizzate per rispondere a una domanda "i benefici giustificano i costi". Per l'ottimizzazione a / vicino a un estremo, se indovini spesso, significa buttare via tutto il tuo lavoro e ricominciare da zero o fallire il progetto (troppo tempo speso per un progetto inutilmente complicato). All'estremo / vicino all'altro estremo è molto più sensato lasciarlo finché non si è in grado di dimostrare che conta usando la misurazione (es. Profilazione).

Purtroppo viviamo in un mondo in cui troppe persone pensano che l'ottimizzazione includa solo le cose (per lo più irrilevanti) all'estremo "banale".


1

È più semplice scrivere codice che non sia né formulato né mantenibile. È più difficile scrivere codice porformante. È ancora più difficile scrivere codice gestibile. Ed è il codice più difficile da scrivere che è sia mantenibile che performante.

Tuttavia, è più facile rendere performante il codice mantenibile, piuttosto che renderlo mantenibile.

Ora, ovviamente, dipende dal tipo di sistema che stai realizzando, alcuni sistemi saranno fortemente critici in termini di prestazioni e necessiteranno di quello pianificato dall'inizio. Per le persone di grande talento come Eric Lippert, che hanno risposto sopra, questi sistemi possono essere comuni; ma per la maggior parte di noi sono la minoranza dei sistemi che costruiamo.

Tuttavia, dato lo stato dell'hardware moderno, nella maggior parte dei sistemi, non è necessario prestare particolare attenzione all'ottimizzazione fin dall'inizio, ma piuttosto evitare la distruzione delle prestazioni è di solito sufficiente. Ciò che intendo con questo è, evitare di fare cose chiaramente stupide come riportare tutti i record di una tabella per ottenere un conteggio anziché semplicemente interrogare select count(*) from table. Evita semplicemente di fare errori e fai uno sforzo per capire gli strumenti che stai usando.

Quindi, prima concentrati su rendere il tuo codice mantenibile. Con questo intendo:

  1. Separare le preoccupazioni il più rigorosamente possibile (ad esempio, non mescolare l'accesso ai dati con la logica aziendale)
  2. Se possibile, fai riferimento a tipi astratti anziché a tipi concreti
  3. Rendi il tuo codice testabile

Il codice gestibile è molto più facile da ottimizzare quando le statistiche mostrano che è necessario.

Successivamente, assicurati che il tuo codice abbia MOLTI test automatici, questo ha diversi vantaggi. Meno bug significa più tempo per ottimizzare, quando necessario . Inoltre, quando esegui l'ottimizzazione, puoi iterare e trovare la soluzione migliore molto più velocemente poiché trovi bug nelle tue implementazioni molto più velocemente.

Gli script di distribuzione automatizzata e l'infrastruttura con script sono anche molto utili per l'ottimizzazione delle prestazioni, poiché, ancora una volta, ti consentono di iterare più velocemente; per non parlare dei suoi altri vantaggi.

Quindi, come sempre, ci sono eccezioni (di cui avrai bisogno di esperienza per identificare meglio), ma, in generale, il mio consiglio è: in primo luogo, impara i tuoi strumenti ed evita i colli di bottiglia delle prestazioni di codifica. In secondo luogo, assicurarsi che il codice sia gestibile. Terzo, test automatizzati. In quarto luogo, distribuzioni completamente automatizzate. Solo dopo aver fatto queste cose, dovresti preoccuparti dell'ottimizzazione.


1

Potrei essere di parte lavorando in aree molto critiche per le prestazioni come l'elaborazione delle immagini e il raytracing, ma direi comunque di ottimizzare "il più tardi possibile" . Indipendentemente da quanto siano importanti le tue esigenze in termini di prestazioni, dopo aver misurato, ci sono sempre più informazioni e chiarezza a posteriori, che in anticipo, il che significa che anche le ottimizzazioni più efficaci vengono in genere applicate in seguito dopo aver acquisito tale conoscenza.

Casi particolari

Ma a volte "il più tardi possibile" è ancora abbastanza dannatamente presto in alcuni casi particolari. Se parliamo di renderer offline, ad esempio, le strutture di dati e le tecniche utilizzate per raggiungere le prestazioni entrano effettivamente nella progettazione dell'utente finale. Ciò può sembrare disgustoso ma il campo è così all'avanguardia e così critico per le prestazioni che gli utenti accettano controlli di fine utente specifici per le tecniche di ottimizzazione applicabili a un particolare raytracer (ad esempio: cache di irradianza o mappatura dei fotoni), poiché alcuni di essi vengono utilizzati alle ore di attesa per il rendering di un'immagine, e altri sono abituati a distribuire enormi somme di denaro per affittare o possedere una fattoria di rendering con macchine dedicate al rendering. C'è una forte riduzione di tempo e denaro per quegli utenti se un renderizzatore offline competitivo può offrire una riduzione non banale del tempo impiegato per il rendering. Questa è una sorta di area in cui una riduzione del 5% nel tempo entusiasma davvero gli utenti.

In casi così particolari, non puoi semplicemente scegliere una tecnica di rendering volenti o nolenti e sperare di ottimizzarla in un secondo momento, poiché l'intero design, incluso il design end-user, ruota attorno alle strutture di dati e agli algoritmi che usi. Non puoi nemmeno semplicemente andare con ciò che ha funzionato bene per le altre persone da qui, tu, come individuo, e i tuoi particolari punti di forza e di debolezza, contribuisci pesantemente a fornire una soluzione competitiva. La mentalità e la sensibilità del principale sviluppatore dietro Arnold è diversa da quelle che lavorano su VRay che hanno utilizzato un approccio molto diverso; non possono necessariamente scambiare posti / tecniche e fare il miglior lavoro (anche se sono entrambi leader industriali). Devi tipo di esperimento, prototipo e benchmark e trovare quello che sei particolarmente bravo a fare dato la serie infinita di tecniche all'avanguardia là fuori se speri di spedire qualcosa di competitivo che effettivamente venderà. Quindi, in questo caso particolare, le preoccupazioni relative alle prestazioni si spostano molto in alto come forse la preoccupazione più importante prima di iniziare lo sviluppo.

Tuttavia, non si tratta necessariamente di una violazione dell'ottimizzazione "il più tardi possibile" , ma solo "il più tardi possibile" è piuttosto precoce in questi casi estremi e peculiari. Capire quando e anche ciò che non ha bisogno di tali problemi prestazionali, se non del tutto, è probabilmente la principale sfida per lo sviluppatore. Cosa non ottimizzare potrebbe essere una delle cose più preziose da imparare e continuare a imparare nella carriera di uno sviluppatore, dal momento che non c'è carenza di sviluppatori ingenui che vogliono ottimizzare tutto (e sfortunatamente anche alcuni veterani che sono riusciti in qualche modo a mantenere il loro lavoro in nonostante la loro contro-produttività).

Il più tardi possibile

Forse la parte più difficile è cercare di capire cosa significa. Sto ancora imparando e sto programmando da quasi tre decenni. Ma soprattutto ora nel mio terzo decennio, sto iniziando a rendermi conto che non è così difficile. Non è scienza missilistica, se ti concentri più sul design che sull'implementazione. Più i tuoi progetti lasciano spazio alle ottimizzazioni appropriate in un secondo momento senza modifiche al design, più tardi puoi ottimizzare. E la produttività sempre maggiore che ho guadagnato alla ricerca di tali progetti che mi offrono quel respiro.

Design che offre spazio di respirazione per ottimizzare in seguito

Questi tipi di progetti in realtà non sono così difficili da realizzare nella maggior parte dei casi se possiamo applicare un po 'di "buon senso". Come storia personale mi piacciono le arti visive come un hobby (trovo che aiuti in qualche modo a programmare software per gli artisti che sono in qualche modo me stesso per capire le loro esigenze e parlare la loro lingua), e ho trascorso un po 'di tempo nei primi anni 2000 usando le applet Oekaki online come un modo rapido per scarabocchiare e condividere il mio lavoro e connettersi con altri artisti.

In particolare il mio sito e la mia applet preferiti erano pieni di difetti prestazionali (qualsiasi dimensione del pennello non banale avrebbe rallentato a una scansione), ma aveva una comunità molto bella. Per aggirare i problemi di prestazione ho usato piccoli pennelli da 1 o 2 pixel e ho semplicemente scarabocchiato il mio lavoro in questo modo:

inserisci qui la descrizione dell'immagine

Nel frattempo continuavo a dare all'autore dei suggerimenti software per migliorare le prestazioni, e notò che i miei suggerimenti erano di natura particolarmente tecnica parlando di ottimizzazioni della memoria e algoritmi e così via. Quindi in realtà mi ha chiesto se fossi un programmatore e ho detto di sì e mi ha invitato a lavorare sul codice sorgente.

Quindi ho guardato il codice sorgente, l'ho eseguito, profilato, e con mio orrore aveva progettato il software attorno al concetto di "interfaccia pixel astratta", come IPixel, che alla fine è stata la causa principale dietro i migliori hotspot per tutto con dinamica allocazioni e invio per ogni singolo pixel di ogni singola immagine. Eppure non c'era modo pratico per ottimizzarlo senza riconsiderare il design dell'intero software perché il design lo aveva intrappolato in un angolo in cui non c'è molto oltre la più banale delle micro-ottimizzazioni quando le nostre astrazioni funzionano al livello granulare di un singolo pixel astratto e tutto dipende da questo pixel astratto.

Penso che sia una violazione del "buon senso", ma ovviamente non è stato un tale buon senso per lo sviluppatore. Ma è come non astrarre cose a un livello così granulare in cui anche i casi d'uso più elementari verranno istanziati da milioni, come con pixel, o particelle, o piccole unità in una gigantesca simulazione dell'esercito. Favorisci IImage(puoi gestire tutti i formati immagine / pixel di cui hai bisogno a quel livello aggregato più voluminoso) o IParticleSystemverso IPixelo IParticle, e quindi puoi inserire le implementazioni più semplici e veloci da scrivere e da capire dietro tali interfacce e avere tutto lo spazio per respirare di cui avrete bisogno per ottimizzare in seguito senza riconsiderare il design dell'intero software.

E questo è l'obiettivo come lo vedo in questi giorni. Escludendo i casi particolari come i renderer offline di cui sopra, progettare con spazio sufficiente per l'ottimizzazione il più tardi possibile, con quante più informazioni di senno di poi possibile (comprese le misurazioni) e applicare tutte le ottimizzazioni necessarie il più tardi possibile.

Naturalmente non sto necessariamente suggerendo di iniziare a utilizzare algoritmi di complessità quadratica su input che raggiungono facilmente una dimensione non banale nei casi comuni dell'utente finale. Chi lo fa comunque? Ma non penso nemmeno che sia un grosso problema se l'implementazione è facile da scambiare in seguito. Questo non è ancora un grave errore se non è necessario riconsiderare alcun progetto.


0

Dipende dal significato di tale prestazione per l'applicazione. E se è persino possibile ottimizzare le prestazioni prima che l'applicazione sia completa funzionalmente.

Molto spesso non dovresti preoccuparti finché non hai niente di meglio da fare, ma potrebbe essere che un certo livello di prestazioni sia fondamentale per il successo della tua applicazione. Se così fosse e sospetti che potrebbe non essere facile, dovresti iniziare a guardare le prestazioni per il bene del "fallimento veloce".

Un principio importante per qualsiasi progetto è quello di concentrarsi prima sulle parti dure. In questo modo, se si scopre che non puoi farlo, lo saprai presto e ci sarà tempo per provare qualcosa di completamente diverso o il progetto potrebbe essere annullato prima che fosse speso troppo.


0

Sto per suggerire che le prestazioni sono più della velocità. Include la scala (da centinaia a migliaia di utenti simultanei). Sicuramente non vuoi che il serbatoio dell'applicazione venga caricato quando riceve un carico di produzione. Le prestazioni includono quanta risorsa (ad es. Memoria) consuma l'applicazione.

Le prestazioni sono anche facilità d'uso. Alcuni utenti preferirebbero che 1 sequenza di tasti esegua un'attività in 10 secondi rispetto a 2 combinazioni di tasti eseguano l'attività in 1 secondo. Per cose del genere chiedi al tuo capo design. Non mi piace portare cose del genere agli utenti in anticipo. Nel vuoto possono dire X ma una volta che stanno lavorando con un pre-rilascio funzionale possono dire Y.

La migliore velocità individuale è quella di contenere una risorsa come una connessione al database. Ma per la scala è necessario acquisire la connessione il più tardi possibile e rilasciarla il più presto possibile. Un viaggio nel database per ottenere 3 cose è più veloce di 3 viaggi separati nel database.

Stai facendo un viaggio per informazioni che non cambiano durante la sessione. In tal caso, ottenerlo all'inizio della sessione e tenerlo premuto è memoria.

Quando si seleziona il tipo di raccolta, considerare la funzionalità, la velocità e le dimensioni.

Sei sicuro di dover conservare gli oggetti in una collezione? Un problema comune è leggere tutte le righe da un file in un elenco e quindi elaborare l'elenco una riga alla volta. È molto più efficiente leggere il file una riga alla volta e saltare l'elenco.

Stai eseguendo il loop tre volte quando puoi eseguire il loop una volta e fare tre cose.

Esiste un punto in cui potrebbe essere necessario elaborare un altro thread con una richiamata. In tal caso, impacchettare il codice tenendo conto di quella possibile esigenza se non interferisce con le esigenze di progettazione immediate.

Molte prestazioni sono anche codice pulito.

C'è un'ottimizzazione prematura e ci sono solo cose di buonsenso che non richiedono davvero più tempo.

Nel database è dove vedo l'ottimizzazione prematura. De-normalizzerà per la velocità prima che si verifichi un problema di velocità. L'argomento che ottengo è se cambiamo la tabella più tardi, allora dobbiamo cambiare tutto. Spesso è possibile creare una vista che presenta i dati in quel modo e potrebbe essere necessario sostituirli in seguito per una tabella non normalizzata.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.