合并排序 - 返回新数组,而不是将合并的数组复制到输入数组
Merge Sort - return a new array instead of copying merged array to input array
我正在尝试实现一个非常幼稚的合并形式(不考虑为此目的考虑所有优化),我的目标是返回合并数组的新副本,而不是传统的通过参考传递输入数组并将合并元素复制到其中的方式。
到此为止,我的代码如下:
vector<int> merge(vector<int> left, vector<int> right)
{
vector<int> result;
int leftIdx = 0;
int rightIdx = 0;
int resultIdx = 0;
while (leftIdx < left.size() && rightIdx < right.size()) {
if (left[leftIdx] < right[rightIdx]) {
result[resultIdx++] = left[leftIdx++];
} else {
result[resultIdx++] = right[rightIdx++];
}
}
while (leftIdx < left.size()) {
result[resultIdx++] = left[leftIdx++];
}
while (rightIdx < right.size()) {
result[resultIdx++] = right[rightIdx++];
}
return result;
}
vector<int> MergeSort(vector<int> intArr)
{
vector<int> recresult;
// base - if array is of length 1, nothing to do, return it as is
if (intArr.size() == 1) {
return intArr;
} else {
int mid = intArr.size() / 2;
// copy left half
vector<int> leftArr(intArr.begin(), intArr.begin() + mid);
// copy right half
vector<int> rightArr(intArr.begin() + mid, intArr.end());
MergeSort(leftArr);
MergeSort(rightArr);
recresult = merge(leftArr, rightArr);
}
return recresult;
}
我知道Merge的此数组是本地数组,因此我将其返回Mergesort,然后将其返回到Main。我假设这不是从中传递和出来的,我错了吗随后的递归电话?
我对此代码的测试输入是{1,0,9}。我应该得到{0,1,9},但我得到32767。
我在这里缺少什么?
MergeSort
递归调用什么都不做,因为 intArr
是通过value (复制)进行的,而您不使用结果值。
类似的东西应该有效:
auto newLeft = MergeSort(leftArr);
auto newRight = MergeSort(rightArr);
recresult = merge(newLeft, newRight);
如评论中提到的Slava,访问result
时还具有UB,因为它的size
为0:
vector<int> result; // size = 0
// ...
result[resultIdx++] = left[leftIdx++]; // UB!
您应该在使用operator[]
访问元素之前调用std::vector::resize
。
首先是merge
-您应该将const引用传递给参数,否则您会制作太多不必要的副本。另外,当您在空白处创建并通过索引访问时,您可以从对result
的界限访问。使用int
进行索引不是一个好主意。因此简化的版本可能是:
vector<int> merge(const vector<int> &left, const vector<int> &right)
{
vector<int> result;
auto lit = left.begin();
auto rit = right.begin();
while( lit != left.end() || rit != right.end() ) {
bool lft = false;
if( rit == right.end() )
lft = true;
else {
if( lit != left.end() )
lft = *lit < *rit;
}
result.push_back( lft ? *lit++ : *rit++ );
}
return result;
}
或更接近您的版本:
vector<int> merge(const vector<int> &left, const vector<int> &right)
{
vector<int> result( left.size() + right.size() );
auto rst = result.begin();
auto lit = left.begin();
auto rit = right.begin();
while( lit != left.end() && rit != right.end() )
*rst++ = *lit < *rit ? *lit++ : *rit++;
std::copy( lit, left.end(), rst );
std::copy( rit, right.end(), rst );
return result;
}
相关文章:
- 合并排序不排序自创建数组类 c++
- 数组为此合并排序函数提供了正确的输出,但向量给出了不正确的输出.出了什么问题?
- 我如何根据 c++ 中的行合并两个 2D 数组
- 使用基于数组的列表 c++ 合并 2 个数组
- 如何在 char 数组中合并两个数组以通过网络发送
- 合并数组的程序打印 0 而不是实际合并的数组
- 如果数组长度为 100000,则使用合并排序对反转进行计数会给出负数
- 合并两个数组后数组大小不正确
- 如何修复合并两个C++数组时'Invalid Pointer'
- 在OpenMP上的并行合并排序上的数组大小问题.如何将合并分类分类为更多任务
- C++全局常量数组:是否保证合并(优化)到一个副本中
- C - 为什么合并函数在递归调用后会逆转数组
- 合并排序 - 返回新数组,而不是将合并的数组复制到输入数组
- C MPI:STD ::在数组上合并
- 合并排序问题,在方法之间传递数组
- C 合并的数组输出错误
- 我如何在INT数组上实现合并排序
- C++将2个已排序的数组合并为1个已排序数组
- 将排序代码与数组合并,陷入合并,只需要一点点修正
- 将字符* 数组合并到uint16_t