Ho letto ogni spiegazione qui ma non ne sono ancora convinto. Penso che il mergesort sia n * n e so che ho torto ma non sono sicuro di dove. Ecco cosa penso:
Supponiamo di ordinare 8 elementi e questo è l'algoritmo (supponendo di avere l'idea giusta per questo):
doSort(int begin, int end, int[] arr) {
if(end != begin) {
int mid = begin + (end - begin)/2;
doSort(begin,mid);
doSort(mid + 1, end);
merge(arr, begin, mid, mid + 1, end);
}
}
merge(int[] arr,int i_begin, i_end, j_begin, j_end) {
// Do the comparison and all that
}
Ora come ho capito la mia fusione () ha la complessità O (n). Ora vediamo quante volte viene chiamato doSort () e quindi merge (). doSort () viene chiamato per i seguenti indici:
- 0-7
- 0-3
- 4-7
- 0-1
- 2-3
- 4-5
- 6-7
Che è 7 volte che è O (n) dato che stiamo ordinando 8 elementi. Allo stesso modo per 16 elementi, l'unione () viene chiamata 15 volte e così via. Quindi, sebbene dividiamo l'array in metà ogni volta, non eliminiamo l'altra metà con qualsiasi mezzo. Confronta questo con una ricerca BST in cui elimino metà dell'albero ad ogni passaggio perché so che l'altra metà è inutile per me, che secondo me è vero log (n). E in caso di un tipo di merge, chiamiamo merge n-1 volte e ogni volta che merge ha bisogno di operazioni o (n), quindi O (n * n).
Dove ho sbagliato? Qualsiasi suggerimento sarebbe apprezzato.