简体   繁体   中英

Performance when adding new elements after existing ones to a LinkedList

Let's assume we have a java.util.LinkedList containing a few hundreds of elements. One possibility to insert a new element E after the an existing element K would be:

list.add(list.indexOf(K) + 1, E);

As far as I understand this method has an O(k 2 ) behavior where k denotes the position of element K. First indexOf() runs through the list until it finds K and afterwards add has to do the same work again until it reaches position k + 1. But the entries which have to be modified could in easily be determined after the first step. I think it wouldn't be that much work to create a method addAfter(K, E) with O(k) behavior.

Is there a way to improve the performance in a scenario like this one besides switching to java.util.ArrayList?

Thank you in advance.

You wrong with your assumption, that it is O(k^2), its just O(2k) which is O(k) (Btw here must be not k=index of element, but size of list, but that doesnt matter for the problem). But you are right it takes twice as long and is inefficent. The only way I can think of is to use ListIterator and find/insert yourself (which is intended to do exactly this kind of manipulations).

As far as I understand this method has an O(k2) behavior where k denotes the position of element K. First indexOf() runs through the list until it finds K and afterwards add has to do the same work again until it reaches position k + 1.

Actually, the cost of list.add(list.indexOf(K) + 1, E) is O(k) if list is a LinkedList .

  • The list.indexOf(K) call involves k link traversals and k comparisons.

  • The list.add(k + 1, E) call involves k + 1 link traversals.

Add them up - 3 k + 1 operations; ie O(k) .


However, you are right. It would be possible to create an alternative version of LinkedList with an addAfter or addBefore method. These methods would also be O(k) but they should be faster. Unfortunately, LinkedList is not implemented in a way that would allow you to simply add these methods (and implement them optimally). The internals of LinkedList are declared as private, so you would need to start over.


And incidentally list.add(list.indexOf(K) + 1, E) on an ArrayList will be O(N) where N is the list length. The indexOf step takes k comparisons, and the add step involves moving N - k elements. Ergo N operations and O(N)

This sample of code is to make k operations:

    LinkedList<Integer> list = new LinkedList<Integer>();
    for(int i=0;i<100;i++){
        list.add(i);
    }

    Integer insert = 1001;
    Integer before = 50;
    for (ListIterator<Integer> iterator = list.listIterator(); iterator.hasNext();) {
        Integer next = iterator.next();
        if(next.equals(before)){
            iterator.add(insert);
            break;
        }
    }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM