0

これは私のプログラムの一部ですが、このプログラムを実行するとセグメンテーション違反が発生します。私はそれを次の行に絞り込みました:

checkBase(ptr1,ptr2)

これらの両方をポインターとして渡します。それらは char* として宣言されており、コンパイル時ではなく実行時エラーです。ファイルが含まれています

< a href = " http://www.google.com "> www.spam.google.com </a >

この場合、ptr1 = www.google.com および ptr2 = spam.google.com

while(inf){

    count++;
    getline(inf, line);
    //cout << "*******" << count << "*******" << endl <<line << endl;
    p = new char[line.length()+1];
    strcpy(p, line.c_str());
    if(strstr(p, "href")){

        ptr = strstr(p, "href");
        while(ptr[0]!='\0'){
            ptr += 1;
            if(ptr[0] == 'w' && ptr[1] == 'w' && ptr[2] == 'w'){
                cout << ptr << endl;            
                ptr = strtok(ptr, "\"");
                cout << "add1   " << ptr << endl;
                add1 = ptr;
                ptr1 = ptr;
                ptr = strtok(NULL, "> ");
                add2 = ptr;
                ptr2 = ptr;
                cout << "ptr1: " << ptr1 << endl << "ptr2: " <<ptr2 << endl;
                if(add1 == add2)
                    cout << "There is an exact match at line: " << count << endl << line << endl;
                else{
                    cout << "in else" << endl;
                    checkBase(ptr1, ptr2); //THIS GIVES A SEGMENTATION FAULT
                }
            }
        }
    }
}

void checkBase(char *add1, char *add2){
    cout << "here" << endl;
    char *base1[1000000], *base2[1000000];
    int count1 = 0, count2 = 0;
    base1[count1] = strtok(add1, ".");
    while(base1[count1] != NULL){
        count1++;
        base1[count1] = strtok(NULL, ".");
        cout << base1[count1] << endl;
    }
    base2[count2] = strtok(add2, ".");
    while(base2[count2] != NULL){
        count2++;
        base2[count2] = strtok(NULL, ".");
    }
    cout << base2[count2-1] << endl;
    if(((strcmp(base1[count1-1],base2[count2-1])) != 0) && (strcmp(base1[count1-2], base2[count2-2]) != 0)){
        //if((strcmp(base1[count1-1], base2[count2-1]) != 0)){
        cout << "Bases do not match: " << endl
             << base1[count1-2] << "." << base1[count1-1] << " and "
             << base2[count2-2] << "." << base2[count2-1] << endl;
        //}
    }
    else{
        cout << "Bases match: " << endl
             << base1[count1-2] << "." << base1[count1-1] << " and "
             << base2[count2-2] << "." << base2[count2-1] << endl;          
    }
}

これがセグメンテーション違反を引き起こしている理由がわかりません。

4

2 に答える 2

3
char *base1[1000000], *base2[1000000];

これがスタックオーバーフローを引き起こしていることは間違いありません。スタックのサイズには制限があり、サイズが数 kb を超える配列を作成することはお勧めできません。たとえば、ヒープに割り当ててみてくださいvector<char *> base1(1000000)

また、必要な正確なサイズを計算し、その量を割り当てるか、ベクターに push_back する必要があります。

于 2013-08-21T02:24:16.700 に答える
0

@Neil Kirkwell によってすでに言及されているスタック オーバーフローを超えた、いくつかの問題

  1. これらは、base1[count1] != NULL; のみを条件とする while ループであってはなりません。また、count1 が配列内の要素数よりも少ないことを確認する必要があります。
  2. count2 または count1 のいずれかが 0 または 1 の場合、-1 および -2 のインデックスを参照しようとすることになります...あまり良くありません。
  3. strrchr を使用して逆方向に検索し、作業を楽にします
  4. これらの配列を完全に構築するのは無駄です。最後の 2 つのトークンだけを気にしているように見えるため、それぞれに 2 つのポインターしか必要ありません。

すなわち

char *one_a = NULL, *one_b = NULL, *two_a=NULL, *two_b = NULL;
char *temp = strtok(add1, ".");
while (temp) {
    one_b = one_a;
    one_a = temp
    temp = strtok(NULL, ".");
}
char *temp = strtok(add2, ".");
while (temp) {
    two_b = two_a;
    two_a = temp
    temp = strtok(NULL, ".");
}
//now just compare one_a with two_a and one_b with two_b and you're done.
于 2013-08-21T17:03:52.900 に答える