2

私は学生を一覧表示するプログラムを持っています。新しい学生を追加したり、学生番号でリストから学生を検索したり削除したりできます。学生情報の構造体が含まれています。すべての情報は REG.DAT という名前のファイルにあります。私の問題は >>DELETE<< の部分にあります。学生番号でリストから学生を削除したいのですが、これを行うと、削除する必要がある人までリストの残りを失いました。この問題を解決するのを手伝ってください。ここに私のコードがあります:

void _remove()
{
    int std_num = 0 , k ;
    int status = 1 , i = -1 , j = 0  ; 
    struct students read[100] ,temp;
    FILE *p ;

    p = fopen("reg.dat","rb");
    if(!p)
    {
        system("cls");
        cout << ">>>>>Register file could not be opened! call the support .<<<<<" << endl;
        _menu();
    }
    while(!feof(p))
    {
        fread(&read[i],sizeof(struct students),1,p) ;
        i++;
    }
    cout << "Enter STD NO. to delete from the list : " << endl ;
    cin >> std_num ;
    for( j = 0 ; j < i ; j++)
    {
        if(std_num == read[j].std_num)
        {
            for( k = j + 1 ; k < i ; k++)
            {
                memcpy(&read[k-1] , &read[k],sizeof (students));
            }
        }
    }
    fclose(p);

    FILE *fp;
    fp = fopen("reg.dat","wb"); 
    for( int l = 0 ; l < i - 2 ; l++)
        fwrite(&read[l], sizeof(struct students), 1 ,fp );
    fclose(fp);
    system("cls") ;
    cout << "STD with NO. " << std_num << " has been removed" << endl ; 
    _menu();
}
4

2 に答える 2

3

memcpy重複するメモリセクションには使用しないでください。代わりにmemmovを使用する必要があります。memmovの説明が述べているように:

メモリのブロックの移動ソースが指す場所から宛先が指すメモリブロックにnumバイトの値をコピーします。コピーは、中間バッファが使用されているかのように行われ、宛先とソースが重複する可能性があります。

また: -学生番号を見つけたら、ステートメントを
使用して最初のループの反復を停止できます。break

よろしく、
ボー

于 2012-06-08T06:30:21.120 に答える
1

通常のアプローチは

  • bool is_deletedにメンバーを追加しstruct studentます。
  • 学生を削除するときは、is_deletedtrueに設定して構造体を更新します。
  • 学生の記録を読むときは、削除されたものを無視してください。
  • ファイルレコード全体をレコードごとに読み取り、削除されたレコードをスキップして別のファイルにコピーする手順を提供します。次に、この他のファイルの名前を元の名前に変更します。この手順は、定期的に、プログラムの起動時に、または必要に応じて手動でのみ呼び出してください。
于 2012-06-08T06:26:23.010 に答える