Le risposte finora utilizzano/emulano tipi di dati mutabili, ma che aspetto ha un approccio funzionale?
Per vedere, diciamo scomporre il problema in alcuni componenti funzionali:
eliminazione gaussiana comporta una sequenza di operazioni di riga, quindi è utile prima di definire una funzione prendendo 2 righe e fattori di scala, e restituendo la riga risultante risultato dell'operazione
Le operazioni di riga che vogliamo devono eliminare una variabile (colonna) da una particolare riga, quindi consente di definire una funzione che prende una coppia di righe e un indice di colonna e utilizza l'operazione di riga precedentemente definita per restituire la riga modificata con quello colonna zero.
Quindi definiamo due funzioni, una per convertire una matrice in forma triangolare, e l'altra per sostituire una matrice triangolare alla forma diagonale (utilizzando le funzioni definite in precedenza), eliminando a turno ciascuna colonna. Potremmo scorrere o ricorrere alle colonne e la matrice potrebbe essere definita come un elenco, vettore o array di liste, vettori o matrici.L'input non è cambiato, ma viene restituita una matrice modificata, quindi possiamo finalmente fare:
let out_matrix = to_diagonal (to_triangular in_matrix);
Ciò che lo rende funzionale non è se i tipi di dati (matrice o elenco) sono mutabili, ma in che modo vengono utilizzati. Questo approccio potrebbe non essere particolarmente 'intelligente' o essere il modo più efficiente per eseguire eliminazioni gaussiane in OCaml, ma l'uso di funzioni pure consente di esprimere l'algoritmo in modo pulito.
fonte
2011-10-21 20:47:14
in realtà 'let compare = compare' dovrebbe essere abbastanza – newacct
alternativamente, si può usare un' Hashtbl' e non è necessario occuparsi di questa roba – newacct
Sì, vero per 'compare'. Riguardo al 'Hashtbl': l'intero punto della domanda era di rimanere in un paradigma funzionale. 'Hashtbl' sono mutabili, quindi sei di nuovo in un' array'. – nlucaroni