Sulla Perfezione

Durante il mio lavoro di sviluppatore mi capita di discutere con i miei colleghi della qualità del software che realizziamo. Ci chiediamo se sia possibile realizzare un software “perfetto”. Con perfetto non intendo esente da bug (caratteristica che, da quello che so, è matematicamente impossibile da dimostrare). Intendo invece la soluzione che tra tutte le possibili soluzioni funzionanti è quella più efficiente, quindi quella che riesce a risolvere il problema con il minor uso possibile di risorse (tempo, memoria, cpu, etc…). Naturalmente potrebbero esistere N soluzioni, alcune più esose di certe risorse, altre più esose di altre risorse. Potremmo dire che queste soluzioni sono tutte perfette, e si equivalgono tra loro. Oppure potremmo scegliere quella che ci fa risparmiare la risorsa che nella specifica situazione è considerata più preziosa.

Quando mi trovo di fronte ad un nuovo problema da risolvere cerco sempre di individuare la soluzione “perfetta”. Tuttavia le soluzioni candidate ad essere perfette hanno spesso delle conseguenze che, in qualche modo, mi fanno desistere dallo sceglierle. Ad esempio qualche riga di codice non chiara, che potrebbe mettere in difficoltà un altro sviluppatore che dovrà lavorarci in futuro. Oppure mi rendo conto che se i requisiti del software cambiassero, la soluzione perfetta sarebbe da cestinare completamente, mentre altre soluzioni (non perfette) potrebbero adattarsi con poco sforzo.

I miei colleghi, che hanno molta più esperienza di me, affermano che il software perfetto non esiste, e bisogna sempre scendere a compromessi. Credo anche io che questo sia vero, ma vorrei esporre una considerazione.

Il termine sistema può essere generalizzato. Ad esempio anche un essere vivente, un animale, una pianta, sono sistemi. Una società è un sistema, o anche un sistema economico. Generalizzando un sistema è un meccanismo che risolve uno o più problemi. Tutti questi sistemi sono sempre immersi in un ambiente con il quale devono interagire. Ad esempio l’atmosfera nel quale è immerso un animale ha determinate caratteristiche: pressione, temperatura, composizione chimica… Un sistema economico dovrà vedersela con i fattori ambientali che influiscono sulla produzione dei beni, come il maltempo o eventi disastrosi. Un sistema informatico può avere un certo numero di utenti contemporanei, risorse limitate, etc…

L’ambiente può essere fisso oppure dinamico. Ad esempio la temperatura dell’aria può rimanere costante oppure variare. La quantità di dati che deve processare un software può essere costante oppure cambiare nel tempo. Qui arriviamo al punto importante: quando costruiamo un sistema, ci interessa che funzioni bene, ma anche che sia in grado di adattarsi ai cambiamenti ambientali.

Abbiamo definito perfetto un sistema in grado di risolvere i suoi problemi nel modo più efficiente possibile, ma i problemi da risolvere dipendono dall’ambiente. Ad esempio un essere vivente può sopravvivere ad una data temperatura, implementando un meccanismo che è il migliore per quella temperatura, quindi è perfetto. Ma appena la temperatura cambia, la soluzione non è più la migliore, e addirittura il sistema potrebbe non sopravvivere al nuovo ambiente.

Quello che vorremmo è un sistema perfetto che, nel momento in cui l’ambiente cambia, si adatta, assumendo una nuova forma perfetta rispetto al nuovo ambiente. A questo punto ci si chiede se è ciò sia possibile. Se prendiamo un sistema perfetto ma non adattabile, e introduciamo il requisito dell’adattabilità, stiamo introducendo ulteriore complessità nel sistema, per cui è possibile che il risultato sia un sistema adattabile ma non più perfetto.

Un esempio più pratico è un software il cui compito è fare la somma di N numeri. Il programma ad un certo punto dovrà memorizzare il totale della somma. Se siamo sicuri che il totale sia minore o uguale al massimo consentito dalla memoria, non abbiamo bisogno di controllare un eventuale overflow. Ma se domani l’ambiente cambia, e il totale può superare la memoria allocata, il sistema fallisce. Possiamo quindi costruire un sistema adattabile, che impedisce un overflow (anche semplicemente con un messaggio di errore). Ma in questo caso abbiamo introdotto un’ulteriore istruzione, che rende il software più lento, anche se solo di poco. Per cui, rispetto al caso di un totale inferiore al massimo, non è perfetto.

Non sono riuscito a trovare un ragionamento logico in grado di dimostrare che sia impossibile realizzare un sistema perfetto e adattabile, ma ad intuito credo che in molti casi questo non sia possibile. O è perfetto, oppure è adattabile.

Per tornare un po’ con i piedi in terra, possiamo trarre da questo ragionamento una conclusione pratica. Quando progettiamo un sistema dobbiamo considerare due aspetti: la sua “vicinanza” alla perfezione, e la sua adattabilità. La cosa migliore è decidere quanto deve essere adattabile il sistema, in base ai cambiamenti che ci aspettiamo possano avvenire nell’ambiente. Fatto questo potremmo capire quanto vicino alla perfezione possiamo avvicinarci.

Quindi, per rispondere alla domanda iniziale, la perfezione esiste, ma è praticamente inutile.