2013-06-17 16 views
5

ho bisogno di inserire un elemento di tipo Person (la mia classe definita) in un ArrayList al indice iAggiungi elemento in un ArrayList in modo efficiente a un determinato indice in Java

So che posso usare add(int index, E element).

Ma esiste un metodo efficace per farlo, poiché nella mia lista si impiegano mediamente circa 1,5 ms (dati raccolti oltre 1000 inserimenti e poi medi).

+0

Bene, quanto è grande la tua lista? Se inserisci i dati in una lista molto ampia, copi molti dati ... –

+0

Vuoi dire - esiste una implementazione di lista più efficiente per l'inserimento? –

+0

Sarei sorpreso se ci sarebbe un modo più efficiente usando ArrayList. Le funzioni principali dovrebbero essere ottimizzate bene. Inoltre consideri 1,5 ms lenti? –

risposta

0

Questo inserimento avviene in O (n) perché deve spostare tutti gli elementi verso il basso e nel peggiore dei casi lo spostamento di ogni elemento verso il basso. (Corretto java dice che è O (n) perché usano una formula matematica da inserire)

Se si desidera un inserimento veloce, aggiungerlo alla fine dell'array o utilizzare una hashmap che è un tempo costante.

Inserire nel hashmap: HashMap peopleMap = new HashMap .....

peopleMap.put (person.name, persona); // (o quello che si desidera tracciare)

Imposta la chiave per il nome delle persone e il valore per persona.

Si può anche provare una hashmap con chiave (ehatver che si desidera tracciare) e valutare l'indice in cui la persona si trova in una matrice di supporti. L'inserto è O (i), look O (i) e puoi anche ordinarlo (lo lascerò come esercizio al lettore)

Se l'intero scopo di questo è di ordinare, quindi per semplicità è possibile inserire in una priorityQueue (nLogn) quindi inserire tutto nell'array che fornirà un array ordinato

+0

puoi dare un esempio di codice per usare hashmap per questo ... – learner

+0

come può essere O (n^2) Ho bisogno di spostare l'array completo inizierò dalla fine. Immagino che questo sia il modo in cui System.arraycopy funziona ed è davvero veloce – learner

+0

'put (indice, valore);' dove index è la chiave –

6

Se l'attività è più intensiva di inserimento/eliminazione, è sempre possibile utilizzare java.util.LinkedList.

  • ArrayList ha una dimensione limitata. Ogni volta che aggiungi un elemento, Java garantisce che possa adattarsi, quindi cresce ArrayList. Se ArrayList cresce più rapidamente, si verificherà un sacco di copie di array.
  • LinkedList aggiunge semplicemente l'elemento alla posizione corretta (collegando i nodi intorno), senza aumentare e copiare l'intera ArrayList.
  • I svantaggi di LinkedList si verificano quando si cerca un elemento. Dal momento che non ha indici, deve attraversare dall'inizio alla fine della lista per trovare un oggetto.

Per LinkedList:

  • ottenere è O (n)
  • aggiuntivo è O (1)
  • remove è O (n)
  • Iterator.rimuovere è O (1)

Per ArrayList:

  • get è O (1)
  • aggiunge è O (1) ammortizzato, ma O (n) nel caso peggiore poiché la matrice deve essere ridimensionato e copiato
  • remove è O (n)
+0

Ho bisogno di fare prima una ricerca binaria per trovare l'indice e quindi inserire, Non riesco a usare la lista come quello che sto facendo è inserire in tableview che usa l'arraylist come modello sottostante (ObservableList ). – learner

+0

Puoi essere più specifico su TableView? – darijan

+2

Questa è una copia di questa [risposta] (http://stackoverflow.com/questions/322715/when-to-use-linkedlist-over-arraylist) (che è molto più dettagliata) –

-1

Se si aggiungono utilizzando

arryListInstance.add(positionIndex, Object); 

l'oggetto verrà aggiunto dopo aver setacciato gli oggetti esistenti di 1 posizione. Pertanto il caso medio di questa operazione diventa O (n).

Mentre semplice add

arryListInstance.add(positionIndex, Object); 

aggiunge l'oggetto alla fine del arrayListInstance. Nel migliore dei casi questa operazione è O (1), ma nel peggiore dei casi diventa O (n) quando viene raggiunta la capacità massima: una nuova istanza ArrayList viene creata internamente e tutti i contenuti vengono copiati.

Si trovano ad affrontare questo problema perché uno dei due motivi di cui prima può essere evitato:

  1. Non hai definito capacità iniziale sufficiente per l'oggetto ArrayList. Pertanto, prima di ogni arrayListInstance.add (positionIndex, oggetto) un nuovo arrayListInstance si sta creando con maggiore capacità e quindi gli elementi esistenti dall'elenco originale vengono copiati e infine aggiungere è in corso. Questo può essere evitato, se si conosce esattamente la quantità di dati che si desidera gestire da questo elenco e definire di conseguenza la capacità iniziale (uguale al numero di possibili elementi). Se non si prevede la capacità iniziale, è meglio elaborare i dati nei lotti .
  2. Dopo ogni inserimento in qualsiasi posizione tranne l'ultima causa, setacciamento di elementi esistenti. Questo è inevitabile. Pertanto, arrayListInstance.add (positionIndex, oggetto) verrà eseguito in O (n) tempo se positionIndex non è l'ultimo indice di arrayList. Anche se si utilizza LinkedList non è possibile ottenere un'operazione di aggiunta di tempo costante che aggiunge un elemento all'elenco a un indice diverso dall'ultimo elemento.
+1

Stai utilizzando lo stesso add in entrambi i casi, quindi il down vote. La seconda aggiunta non è l'aggiunta "semplice". –

Problemi correlati