Mergesort有一个半尺寸的帮助向量

时间:2017-08-23 15:55:51

标签: c++ mergesort

我一直在尝试使用仅需要排序的矢量大小一半的帮助向量来优化mergesort实现。它应该是可能的,但我没有看到它。 普通合并使用全​​尺寸的帮助向量,在原始向量上有2个迭代器,一个从左侧站点开始,一个刚好在(或者过去,如果向量具有偶数大小)中间。

全尺寸帮助向量合并

void TDMergeSort<T>::merge(vector<T>& v, int links, int midden, int rechts, vector<T>& hulp) const{
        int j = links;
        int li = links;
        int ri = midden;
        while (li < midden && ri < rechts) {
            if (v[li] < v[ri]) {
                hulp[j++] = v[li++];
            } else {
                hulp[j++] = v[ri++];
            }
        }

        while (li < midden) {
            hulp[j++]=v[li++];
        }
        while (ri < rechts) {
            hulp[j++]=v[ri++];
        }
    for(int i=links;i<rechts;i++){
        v[i]=move(hulp[i]);
    }
}

如何将此转换为hulp不是v.size()的版本,而是v.size()/ 2?

1 个答案:

答案 0 :(得分:0)

一旦我使用类似的方法来解决HackerRank问题(请参阅下面的方法以适应您的方法):

void merge(std::vector<int>& original, long long left, long long middle, const long long end) {
    const std::vector<int> leftSide({original.begin()+left, original.begin()+middle});
    const std::vector<int>& rightSide=original; // just to make the code clearer
    auto posForward=left;
    auto right=middle;
    // reset left offsets because we are using a new collection
    middle -= left, left = 0;
    for ( ; left < middle && right < end; ++posForward) {
        if (leftSide[left] <= rightSide[right]) {
            original[posForward] = leftSide[left++];
        } else {
            original[posForward] = rightSide[right++];
            // inversions += (middle-left); // info: removed for this SO answer
        }
    }
    while (left < middle) {
        original[posForward++] = leftSide[left++];
    }
    while (right < end) {
        original[posForward++] = rightSide[right++];
    }
}

您可以看到完整的程序here

适合您需求的代码:

void TDMergeSort<T>::merge(vector<T>& v, int links, int midden, int rechts, vector<T>& hulp) const {
    hulp = {v.begin()+links, v.begin()+midden};
    int j = links;
    int ri = midden;
    midden -= links;
    int li = 0;

    while (li < midden && ri < rechts) {        
        if (hulp[li] <= v[ri]) {
            v[j++] = hulp[li++];
        } else {
            v[j++] = v[ri++];
        }
    }

    while (li < midden) {
        v[j++]=hulp[li++];
    }
    while (ri < rechts) {
        v[j++]=v[ri++];
    }
}