簡體   English   中英

提高合並兩個ArrayList的性能

[英]Improving the performance of merging two ArrayLists

我將兩個ArrayList與以下代碼合並。 該代碼正在運行,並且給了我想要的結果,但是我想要一個更高效的版本。 這是條件。

  1. 方法接受兩個列表,並且兩個列表都具有降序排列的元素(5,4,3,2)
  2. 方法接受一個整數來確定所得ArrayList的大小。
  3. 第一個輸入列表的大小永遠不會大於結果ArrayList的大小。

碼:

public ArrayList<Integer> mergeList(ArrayList<Integer> first,ArrayList<Integer> second, int n){
    //case 1: when both list are null.
    if(first == null && second == null )
        return null;
    //case 2: when first list is null but second list have elements
    else if( first == null && second != null){
        return second.size() >=n ? new ArrayList<Integer>(second.subList(0, n)) : second;
    }
    //case 3: when first list have record and second list is null
    else if(first != null && second == null){
        return first;
    }
    //case 4: when both list have elements 
    else {
        first.addAll(second);
        Collections.sort(first);
        Collections.reverse(first);
        return first.size()>=n ? new ArrayList<Integer>(first.subList(0, n)) : first;
    }
}

}

這取決於您所說的“更有效”。

在什么方面呢? 內存,CPU,可讀性?

根據上面的代碼,我做出以下假設:

  • 在沒有任何性能分析測量/需求的情況下,可讀性比純粹的性能/內存消耗更為重要。“程序優化的第一條規則:不要這樣做。程序優化的第二條規則(僅適用於專家!):請不要這樣做。 “ —邁克爾·傑克遜(Michael A. Jackson)
  • 優先使用null對象模式而不是返回null
  • 重復元素是理想/必需
  • 使用比較器執行反向排序

private List<Integer> mergeList(List<Integer> list1, List<Integer> list2, final int newSize) {

    // Enforce null object pattern
    if (list1 == null) {
        list1 = Collections.emptyList();
    }
    if (list2 == null) {
        list2 = Collections.emptyList();
    }

    // If duplicates are not desirable, a TreeSet would perform automatic sorting.
    List<Integer> result = new ArrayList<Integer>(list1);
    result.addAll(list2);

    Comparator<Integer> reverseSortComparator = new Comparator<Integer>() {

        @Override
        public int compare(final Integer o1, final Integer o2) {
            return o2.compareTo(o1);
        }
    };

    Collections.sort(result, reverseSortComparator);

    if (result.size() > newSize) {
        return result.subList(0, newSize);
    } else {
        return result;
    }
}

看來您要保留firstsecond的內容。 如果您不是這樣,那么這對您就很好了,並且可以使您的代碼更快,更易讀:

public ArrayList<Integer> mergeList(ArrayList<Integer> first,ArrayList<Integer> second, int maxLength){

    //case 1: when both list are null.
    if(first == null && second == null )
        return null;
    //case 2: when first list is null but second list have elements
    else if( first == null && second != null){
        return second;
    }
    //case 3: when first list have record and second list is null
    else if(first != null && second == null){
        return first;
    }
    //case 4: when both list have elements 
    else if(first != null && second != null){
        first.addAll(second);
        Collections.sort(first); //want to merge these two line into one
        Collections.reverse(first);
    }
    return (ArrayList) first.size() > maxLength ? first.subList(0, n) : first;
}

之所以更快,是因為對於每個addAll() ,Java必須遍歷所有項目,並將它們復制到tempList 我保留了Collections.reverse調用,因為您似乎需要按反向排序的順序處理數據。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM