嘣叽 2026-03-12 01:25 采纳率: 60%
浏览 8
已结题

PTA-找出不是两个数组共有的元素:为什么提示我段错误?

PTA-找出不是两个数组共有的元素:为什么提示我段错误?

题目详情:
给定两个整型数组,本题要求找出不是两者共有的元素。

输入格式:
输入分别在两行中给出两个整型数组,每行先给出正整数N(≤20),随后是N个整数,其间以空格分隔。

输出格式:
在一行中按照数字给出的顺序输出不是两数组共有的元素,数字间以空格分隔,但行末不得有多余的空格。题目保证至少存在一个这样的数字。同一数字不重复输出。
输入样例:
10 3 -5 2 8 0 3 5 -15 9 100
11 6 4 8 2 6 -5 9 0 100 8 1
输出样例:
3 5 -15 6 4 1
我的代码:

#include <stdio.h>

int main(){
    int N1;
    scanf("%d", &N1);
    int a[N1];
    for(int i = 0; i < N1; i++){
        scanf("%d", &a[i]);
    }
    //第一组输入
    int N2;
    scanf("%d", &N2);
    int b[N2];
    for(int i = 0; i < N2; i++){
        scanf("%d", &b[i]);
    }
    //第二组输入

    int shuchu[10000];    //-5000至4999,用来标记是否已经输出过
    int first = 1;
    int same = 0;
    for(int i = 0; i < N1; i++){
        for(int j = 0; j < N2; j++){
            if(b[j] == a[i]){
                same = 1;
                break;
            }
        }
        if(!same){
            //先判断,如果没输出过就输出,防重复
            if(shuchu[a[i]+5000] == 0){
                if(first){
                    printf("%d", a[i]);
                    first = 0;
                }
                else{
                    printf(" %d", a[i]);
                }
            }
            shuchu[a[i]+5000] = 1;
        }
        same = 0;
    }
    //先输出第一组中不共有的元素
    
    same = 0;
    for(int i = 0; i < N2; i++){
        for(int j = 0; j < N1; j++){
            if(b[i] == a[j]){
                same = 1;
                break;
            }
        }
        if(!same){
            if(shuchu[b[i]+5000] == 0){
                if(first){
                    printf("%d", b[i]);
                    first = 0;
                }
                else{
                    printf(" %d", b[i]);
                }
            }
            shuchu[b[i]+5000] = 1;
        }
        same = 0;
    }
    //输出第二组中不共有的元素
    
    return 0;
}

结果:

alt

  • 写回答

2条回答 默认 最新

  • 关注

    你代码里的 shuchu[10000] 数组下标是 0~9999,对应数字范围 -5000~4999
    一旦输入的数小于-5000或大于4999a[i]+5000 就会越界,访问非法内存,直接触发段错误


    改法(两种任选)

    方案1:规避越界(推荐,改动最小)

    shuchu 数组开得足够大,比如覆盖 -1e5~1e5

    int shuchu[200001] = {0}; // 下标 = num + 100000,覆盖-100000~100000
    

    然后把所有 shuchu[x+5000] 改成 shuchu[x+100000] 就行。

    方案2:先存后去重(更安全)

    先把所有不共有的元素存到临时数组,最后遍历去重输出,完全不用管数字范围:

    int res[40], cnt = 0;
    // 收集所有不共有的元素到res
    // 再遍历res去重输出
    

    一句话总结

    • 原问题:数组越界,数字超出 -5000~4999 就炸。
    • 解决:要么把 shuchu 数组开大,要么换“先存后去重”的写法。
    • 改完就能过所有测试点,不会再段错误。
    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(1条)

报告相同问题?

问题事件

  • 系统已结题 3月20日
  • 已采纳回答 3月12日
  • 创建了问题 3月12日