成长之路,刷题第一步,快行动起来吧 !
题目:
给出一个有序的整数数组 A 和有序的整数数组 B ,请将数组 B 合并到数组 A 中,变成一个有序的升序数组
1.保证 A 数组有足够的空间存放 B 数组的元素, A 和 B 中初始的元素数目分别为 m 和 n,A的数组空间大小为 m+n
2.不要返回合并的数组,将数组 B 的数据合并到 A 里面就好了,且后台会自动将合并后的数组 A 的内容打印出来,所以也不需要自己打印
3. A 数组在[0,m-1]的范围也是有序的
牛客网链接 :
思路:
这里考虑使用归并的思想,先开辟一个可以存放两数组数据个数的新数组,这里用两个指针对两个数组同时去遍历。两个指针所对应的数据进行对比,就找小的数据往新数组里放,然后被换数组数据指针向后走一步,再进行对比依次循环。因为它们本身就是有序的,这样一定可以保证新数组里的数据是有序的。这样遍历总有一个数组先访问完,那么就把没有遍历完的数组数据全拷贝到新数组里去。最后把新数组里的数据再拷入到原数组。
特殊情况 :
如果第一个数组里没有数据,就直接把第二个数组数据拷入到第一个数组
如果第二个数组没有数据,那么就直接返回,不需要进行操作
代码实现:
这里没有使用ALen和BLen是因为第一个数组有效数据个数m和第二个数组有效数据n的和就可以表示新数组的大小。
void merge(int* A, int ALen, int m, int* B, int BLen, int n) {
if (n == 0)//如果第二个数组为空
{
return;
}
if (m == 0)//如果第一个数组为空
{
int j = 0;
for (j = 0; j < n; j++)
{
A[j] = B[j];
}
}
else
{
int* tmp = (int*)malloc(sizeof(int) * (m + n));
int begin1 = 0;
int begin2 = 0;
int index = 0;
while (begin1 < m && begin2 < n)//两数组同时进行遍历
{
if (A[begin1] < B[begin2])
{
tmp[index++] = A[begin1++];
}
else
{
tmp[index++] = B[begin2++];
}
}
while (begin1 < m)//如果第二个数组先遍历结束
{
tmp[index++] = A[begin1++];
}
while (begin2 < n)//如果第一个数组先遍历结束
{
tmp[index++] = B[begin2++];
}
//拷贝回原数组
int i = 0;
for (i = 0; i < m + n; i++)
{
A[i] = tmp[i];
}
}
free(tmp);
}
}
小结:
考虑问题定要全面,一定要考虑特殊情况,边界的控制。加油!