鱼C论坛

 找回密码
 立即注册
查看: 1289|回复: 4

[已解决]SOS:用C编写函数出现错误,求解决~

[复制链接]
发表于 2019-3-14 11:49:10 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
函数要求1:编写函数 int mergearr( int a[], int m, int b[], int n),将两个严格增序数组a[],b[]合并,并保证合并后数组严格增序,函数值返回合并后的数组a[]中元素个数。
函数要求2:不能定义额外新数组
由于本人才开始学习C,经常出现各种BUG,却不知道错在哪,请各位大佬帮忙~
本人思路文字描述:将b[]中小于a[i]的元素按序插入数组a,大于a[m]的元素插入a[]尾部。

        i=0,j=0;
        a[i]与b[j]进行循环对比(i<a[]长度,j<b[]长度):
        1,如果a[i]<b[j]时,a[i]位置不变,i++后重新对比;
        2,如果a[i]=b[j]时,a[i]不变,i++;j++后重新对比;
        3,如果a[i]>b[j]时,数组a[]中第【i】位元素之后整体后移一位,再将b[j]赋值给a,数组a[]长度++;j++后重新对比。
        循环后两种情况:
        1,数组a[]包含所有数组b[]元素,实现函数要求。
        2,数组a[]未包含所有b[]元素,需要将数组b[]剩余元素插入数组a[]尾部,实现函数要求。
#include<stdio.h>
int mergearr(int a[],int m,int b[],int n)
{
        int i=0,j=0,k,len=m;//m是数组a[]初始长度,len是a[]可变长度。
        printf("函数内m=%d,n=%d\n",m,n);//验证函数各项数值,可忽略。
        while(i<len&&j<n)//while循环逐一判断数组a,b中的元素大小
        {
                if(a[i]<b[j])
                {
                        i++;
                }
                else if(a[i]==b[j])
                {
                        i++;j++;
                }
                else if(a[i]>b[j])
                {
                        for(k=len;k>i;k--)//数组a[]从a[i]之后整体后移
                        {
                                a[k]=a[k-1];
                        }
                        a[i]=b[j];//插入b[j]
                        len++;
                        j++;
                }
        }
        printf("j=%d,a[len-1]=%d,b[j]=%d,len=%d\n",j,a[len-1],b[j],len);//验证函数各项数值,可忽略。
        while(a[len-1]<b[j]&&j<n)//循环判断数组a[]是否包含全部数组b[],并将剩余数组b[]元素插入数组a[]尾部。
        {
                a[len]=b[j];
                len++;
                j++;
        }
        printf("j=%d,a[len-1]=%d,b[j]=%d,len=%d\n",j,a[len-1],b[j],len);//验证函数各项数值,可忽略。
        printf("函数内m=%d,n=%d\n",m,n);//验证函数各项数值,可忽略。
        for(i=0;i<len;i++)
        {
                printf("%d,\n",a[i]);
        }
        return len;
}
int main()
{
        int i,j,p,q,length;
        int c[]={1,2,3,5,7,9};
        int d[]={2,4,5,6,8,9,10};
        p=sizeof(c)/sizeof(c[0]);//求c[]长度
        q=sizeof(d)/sizeof(d[0]);
        printf("调用前p=%d,q=%d\n",p,q);//验证函数各项数值,可忽略
        int mergearr(int a[],int m,int b[],int n);
        length=mergearr(c,p,d,q);
        printf("length=%d\n",length);
        printf("调用后p=%d,q=%d\n",p,q);//验证函数各项数值,可忽略
        for(i=0;i<length;i++)
        {
                printf("%d,",c[i]);
        }
}

输出结果如下:
[/i][/i][/i][/i][/i][/i][/i] QQ截图20190314113903.png 这里:调用后p=10,以及最后输出的结果1,2,3,4,5,6,7,8,10,10均不是想要的答案,却不知道在哪里出错,如何更改,请各位大佬帮忙。

最佳答案
2019-3-14 14:13:52
本帖最后由 jackz007 于 2019-3-14 14:17 编辑
路易大魔王 发表于 2019-3-14 13:29
emmmm  有两个地方不明白,第一个是为何用const,第二个是我将函数替换我原来函数之后,p和q的值依然发生 ...


    main() 函数中对 c[] 定义的时候,没有为 d[] 预留空间,导致拼接后 c[] 严重越界
        int c[]={1,2,3,5,7,9};
    所以,我对 main() 也做了修改:
#include <stdio.h>

mergearr(int a[] , const int m , const int b[] , const int n)
{
        int i = 0 , j = 0 , k                               ;
        for(i = 0 ; i < n ; i ++) a[m + i] = b[i]           ;
        for(i = 1 ; i < m + n ; i ++) {
                j = i                                       ;
                while(j > 0 && a[j] < a[j - 1]) {
                        k = a[j]                            ;
                        a[j] = a[j - 1]                     ;
                        a[j - 1] = k                        ;
                        j --                                ;
                }
        }
        for(i = 0 ; i < m + n ; i ++) printf("%d\n" , a[i]) ;
        return m + n                                        ;
}

main(void)
{
        int i , j , p , q , length                           ;
        int c[20] = {1 , 2 , 3 , 5 , 7 , 9}                  ;
        int d[] ={2 , 4 , 5 , 6 , 8 , 9 , 10}                ;
        p = 6                                                ; // 求c[]长度
        q = sizeof(d) / sizeof(int)                          ;
        printf("调用前 p = %d , q = %d\n" , p , q)           ; //验证函数各项数值,可忽略
        length = mergearr(c , p , d , q)                     ;
        printf("length = %d\n" , length)                     ;
        printf("调用后 p = %d , q = %d\n" , p , q)           ; //验证函数各项数值,可忽略
        for(i = 0 ; i < length ; i ++) printf("%d ," , c[i]) ;
}
        const 的意思是变量在函数内只读,不允许修改,编译程序在检查语法的时候会更加严格。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2019-3-14 12:36:20 | 显示全部楼层
本帖最后由 jackz007 于 2019-3-14 12:42 编辑

    我重写了 mergearr() 楼主可以对照参考
mergearr(int a[] , const int m , const int b[] , const int n)
{
        int i = 0 , j = 0 , k                               ;
        for(i = 0 ; i < n ; i ++) a[m + i] = b[i]           ; // 合并两个数组
        for(i = 1 ; i < m + n ; i ++) {                       // 对合并后的数组排序
                j = i                                       ;
                while(j > 0 && a[j] < a[j - 1]) {
                        k = a[j]                            ;
                        a[j] = a[j - 1]                     ;
                        a[j - 1] = k                        ;
                        j --                                ;
                }
        }
        for(i = 0 ; i < m + n ; i ++) printf("%d\n" , a[i]) ; // 输出
        return m + n                                        ;
}
      我使用 TDM-GCC 编译,需要把 main() 中的 mergearr()  的函数声明删除才能编译通过,就是这一行:
        int mergearr(int a[],int m,int b[],int n);
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2019-3-14 13:29:26 | 显示全部楼层
jackz007 发表于 2019-3-14 12:36
我重写了 mergearr() 楼主可以对照参考

      我使用 TDM-GCC 编译,需要把 main() 中的 mergearr() ...

emmmm  有两个地方不明白,第一个是为何用const,第二个是我将函数替换我原来函数之后,p和q的值依然发生了变化,一直不理解为何p,q值会变。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2019-3-14 14:13:52 | 显示全部楼层    本楼为最佳答案   
本帖最后由 jackz007 于 2019-3-14 14:17 编辑
路易大魔王 发表于 2019-3-14 13:29
emmmm  有两个地方不明白,第一个是为何用const,第二个是我将函数替换我原来函数之后,p和q的值依然发生 ...


    main() 函数中对 c[] 定义的时候,没有为 d[] 预留空间,导致拼接后 c[] 严重越界
        int c[]={1,2,3,5,7,9};
    所以,我对 main() 也做了修改:
#include <stdio.h>

mergearr(int a[] , const int m , const int b[] , const int n)
{
        int i = 0 , j = 0 , k                               ;
        for(i = 0 ; i < n ; i ++) a[m + i] = b[i]           ;
        for(i = 1 ; i < m + n ; i ++) {
                j = i                                       ;
                while(j > 0 && a[j] < a[j - 1]) {
                        k = a[j]                            ;
                        a[j] = a[j - 1]                     ;
                        a[j - 1] = k                        ;
                        j --                                ;
                }
        }
        for(i = 0 ; i < m + n ; i ++) printf("%d\n" , a[i]) ;
        return m + n                                        ;
}

main(void)
{
        int i , j , p , q , length                           ;
        int c[20] = {1 , 2 , 3 , 5 , 7 , 9}                  ;
        int d[] ={2 , 4 , 5 , 6 , 8 , 9 , 10}                ;
        p = 6                                                ; // 求c[]长度
        q = sizeof(d) / sizeof(int)                          ;
        printf("调用前 p = %d , q = %d\n" , p , q)           ; //验证函数各项数值,可忽略
        length = mergearr(c , p , d , q)                     ;
        printf("length = %d\n" , length)                     ;
        printf("调用后 p = %d , q = %d\n" , p , q)           ; //验证函数各项数值,可忽略
        for(i = 0 ; i < length ; i ++) printf("%d ," , c[i]) ;
}
        const 的意思是变量在函数内只读,不允许修改,编译程序在检查语法的时候会更加严格。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2019-3-14 16:40:48 | 显示全部楼层
jackz007 发表于 2019-3-14 14:13
main() 函数中对 c[] 定义的时候,没有为 d[] 预留空间,导致拼接后 c[] 严重越界

    所以,我 ...

明白了,原来我输出错误的原因是因为数组c[]的溢出,可纠结死我了,非常感谢。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-10-3 10:45

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表