È necessaria la transitività per un algoritmo di ordinamento


14

È possibile utilizzare un algoritmo di ordinamento con un confronto non transitivo e, in caso affermativo, perché la transitività è elencata come requisito per i comparatori di ordinamento?

Sfondo:

  • Un algoritmo di ordinamento in genere ordina gli elementi di un elenco secondo una funzione di confronto C (x, y), con

    C(X,y)={-1Se Xy0Se X~y+1Se Xy

    I requisiti per questo comparatore sono, per quanto li capisco:

    • riflessivo: X:C(X,X)=0
    • antisimmetrico: X,y:C(X,y)=-C(y,X)
    • transitivo: X,y,z,un':C(X,y)=un'C(y,z)=un'C(X,z)=un'
    • C (x, y) è definito per tutti x e y, e i risultati dipendono solo da xey

    (Questi requisiti sono sempre elencati in modo diverso in diverse implementazioni, quindi non sono sicuro di averli fatti bene)

Ora mi chiedo una funzione di confronto "tollerante", che accetta i numeri x, y come simili se : |X-y|1

C(X,y)={-1Se X<y-10Se |X-y|1+1Se X>y+1

Esempi: entrambi [ 1, 2, 3, 4, 5]e [1, 4, 3, 2, 5]sono correttamente ordinati in ordine crescente secondo il comparatore tollerante ( se x viene prima di y nell'elenco) ma non lo è, poiché C (4,2) = 1C(X,y)0
[1, 4, 2, 3, 5]

Questo comparatore tollerante è riflessivo e antisimmetrico, ma non transitivo.

cioè C (1,2) = 0, c (2,3) = 0, ma C (1,3) = -1, violando la transitività

Eppure non riesco a pensare a nessun algoritmo di ordinamento che non riuscirebbe a produrre un output "correttamente ordinato" se fornito questo comparatore e un elenco casuale.

La transitività non è quindi richiesta in questo caso? E c'è una versione meno rigida di transitività, che è necessario per la cernita al lavoro?

Domande correlate:


Penso che quicksort con "scegli sempre il centro" per il pivot fallirebbe usando questo comparatore su [3, 2, 1].
G. Bach,

2
Ho il sospetto che alcuni comparatori non transitivi utilizzati in alcuni algoritmi di ordinamento possano causare un ciclo infinito.
Karolis Juodelė,

1
Cosa considereresti un elenco ordinato (ovvero l'output richiesto)? Nel solito caso, ci sono due condizioni equivalenti: e a ia j per tutti i j . un'ioun'io+1un'ioun'jioj
Yuval Filmus,

@ G.Bach Penso che quicksort fallisca completamente se l'array ha n volte 3, una volta 2, n volte 1 e il mezzo 2 viene utilizzato come primo perno, indipendentemente da ciò che accade dopo.
gnasher729,

Risposte:


11

Hai chiesto: possiamo eseguire un algoritmo di ordinamento, alimentandolo come un comparatore non transitivo?

La risposta: certo. È possibile eseguire qualsiasi algoritmo con qualsiasi input.

Tuttavia, conosci la regola: Garbage In, Garbage Out. Se si esegue un algoritmo di ordinamento con un comparatore non transitivo, è possibile ottenere risultati senza senso. In particolare, non vi è alcuna garanzia che l'output verrà "ordinato" in base al comparatore. Pertanto, l'esecuzione di un algoritmo di ordinamento con un comparatore non transitivo non sarà probabilmente utile nel modo in cui probabilmente speravi.

Come controesempio, l'esecuzione dell'ordinamento di inserzione nell'elenco di input usando il tuo comparatore lascerebbe invariato l'elenco - tuttavia l'elenco di output risultante non è in ordine (secondo il tuo comparatore).[3,2,1]


1
il mio primo pensiero è stato che l'elenco [3,2,1] sia in ordine secondo il mio comparatore, quindi ovviamente l'ordinamento dovrebbe lasciarlo invariato; ma avrei potuto usare la definizione errata di ordinato.
Metto

4
@HugoRune Bene, questo è un punto interessante. Che cosa si intende per ordinato ? Se si riesce a mostrare un algoritmo di ordinamento terminerà dato un comparatore non transitiva, e che ogni volta che i termina algoritmo, un po 'di condizione è vera, e questa condizione è quello che prendi ordinando di essere ... poi, naturalmente, che algoritmo ordinare la vostra lista ogni volta, per quella definizione di ordinamento . Se il comparatore non è transitivo, potrebbe non avere senso prendere una definizione di ordinata che richiede un confronto a coppie di tutti gli elementi nella lista ordinata.
Patrick87,

3
@HugoRune, con "vengono confrontati solo i vicini" probabilmente avrai bisogno di un ordinamento personalizzato. Gli algoritmi standard presuppongono la transitività per evitare confronti ridondanti. Oppure puoi incorporare il tuo ordine non transitivo in uno transitivo. O forse stai cercando qualcosa sulla falsariga di un ordinamento topologico ?
vonbrand,

Mi sono imbattuto in questo un po 'di tempo fa e ho scoperto che l'ordinamento a bolle funziona davvero bene, dal momento che confronta solo elementi adiacenti.
Mooing Duck,

4

Dato un insieme di elementi e una relazione di ordinamento binaria, è necessaria la transitività per ordinare totalmente gli elementi. In effetti, è necessaria persino la transitività per definire un ordine parziale sugli elementi. http://en.m.wikipedia.org/wiki/Total_order

Avresti bisogno di una definizione molto più ampia di cosa significhi "ordinato" per ordinare gli elementi senza transitività. È difficile essere coerenti. Un'altra risposta dice "In particolare, non vi è alcuna garanzia che l'output verrà" ordinato "in base al proprio comparatore." Ma in realtà possiamo dire qualcosa di molto più forte. Si garantisce che l'output non viene ordinato in base al proprio comparatore.

un'<BB<cc<un'


1
Ho interpretato la domanda da porre sull'ordinamento usando ordinamenti parziali (in modo tale che i confronti che affermano che le cose sono ineguali sono transitivi, ma quelli che considerano gli oggetti sono indistinguibili non lo sono). L'ordinamento basato su un ordinamento parziale è talvolta utile, ma nel peggiore dei casi richiede confronti N (N-1) / 2. Qualsiasi algoritmo di ordinamento che nel caso peggiore fa meno di N (N-1) / 2 confronti non sarà in grado di classificare correttamente gli articoli parzialmente ordinati per i motivi descritti nella mia risposta.
supercat,

2

Sembra che ciò che desideri sia disporre gli elementi in modo tale che tutte le classifiche riconoscibili siano corrette, ma gli oggetti vicini potrebbero essere considerati "indistinguibili". È possibile progettare algoritmi di ordinamento che funzioneranno con tali confronti, ma a meno che non vi siano limiti al numero di confronti che possono riferire che le cose sono indistinguibili, non c'è modo di evitare che richiedano confronti N (N-1) / 2. Per capire perché, seleziona un numero N e qualsiasi algoritmo di ordinamento che esegua meno di N (N-1) / 2 confronti. Quindi compilare un elenco L [0..N-1], impostando ciascun elemento L [I] su I / N e "ordinandolo" utilizzando il comparatore (il valore minimo sarà 0 e il massimo (N-1) / N , quindi la differenza sarà (N-1) / N, che è inferiore a 1).

Poiché ci sono N (N-1) / 2 coppie di elementi che possono essere confrontati e l'ordinamento non ha fatto molti confronti, ci deve essere una coppia di elementi che non sono stati confrontati direttamente l'uno con l'altro. Sostituisci qualunque di questi abbia finito per essere ordinato per primo con 1 e l'altro con -1 / N, riporta tutti gli elementi nella loro posizione iniziale e ripeti l'operazione di ordinamento. Ogni singola operazione di confronto produrrà zero, proprio come la prima volta, quindi verranno eseguiti gli stessi confronti e gli oggetti finiranno nella stessa sequenza. Affinché l'elenco sia ordinato correttamente, "1" dovrebbe essere ordinato dopo "-1 / N" (poiché differiscono per più di uno) ma poiché l'algoritmo di ordinamento non confronterebbe mai questi due elementi direttamente uno contro l'altro, esso non avrebbe modo di saperlo.


0

Riempi un array di n elementi con i valori n, n-1, n-2, ..., 2, 1. Quindi prova a ordinare usando l'algoritmo "Inserimento diretto". Scoprirai che ogni elemento è considerato uguale all'elemento appena prima di esso e quindi non viene spostato. Il risultato dell '"ordinamento" è lo stesso array.

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.