简体   繁体   中英

Is it more efficient to loop over a list each time or remove elements as I find the one I want in Java?

I have two lists of objects, say of X and Y.

There is a foreign key in objects of Y which show which object of X they are assigned to. This is a one-to-one relationship, no duplicates. As such, each time a Y object is found, it is not needed in the list anymore.

class X {
    Long id;
    Y y;
    ...
}

class Y {
    Long id;
    Long xId;
    ...
}

Would it be more efficient to loop through the list of Y for each object of X, or would it be quicker to remove the Y object from its list?

for(X x: xList) {
    for(Y y: yList) {
        if(y.getXId() == x.getId()) {
            x.setY(y);
            break;
        }
    }
}

vs

for(X x: xList) {
    for(int i = 0; i < yList.size(); i++) {
        Y y = yList.get(i);
        if(y.getXId() == x.getId()) {
            x.setY(y);
            yList.remove(i);
            i--;
            break;
        }
    }
}

With respect to time complexity, both are quadratic, O(n 2 ) . Your second option might 1 be faster in practice, but it is still considered O(n 2 ) .

To make it linear, O(n) , you have to be willing to spend O(n) extra space.

The below code, builds an auxiliary map having instances of X keyed by their id.

Map<Long, X> xObjectsById = xList.stream()
        .collect(Collectors.toMap(X::getId, Function.identity())));

Then, we can loop through Y objects and get the corresponding X from the map.

for (Y y : yList) {
    xObjectsById.get(y.getXId())
            .setY(y);        
}

1 You have measure the performance to conclude this. Moreover, the second option does additional operations of deletion which have to be accounted for. Also how good/bad it performs depends on what sort of list you have.

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