处理c

时间:2016-12-18 14:05:35

标签: c file visual-c++ struct

当我正在处理我的manii项目电话簿时,我在删除功能时遇到一些问题,当有相同名字的多个结果时(我使用名字来搜索我要删除的联系人) 在这种情况下,我在我的结构中创建了额外的变量,称为" ID"和这个ID自动填写我的程序(所以每个用户都有一个唯一的ID),所以我以后可以找到用户想要删除它的结果,它工作正常,但当我从文件中删除一个联系人它离开我有间隙,这对下一次接触有影响 例如:

  

我有3个联系人,每个人有一个iD 1,2和3,当我删除No.2时,它变为1和3,当我添加一个新用户时,我的自动填充循环将计算联系人的数量(2 )并给新的ID为3,这给我留下3个ID为1,3和3的联系人,这是错误的

所以我想在每次删除操作后重置所有ID,这对我来说似乎很好,这几行应该这样做,我不知道为什么这部分不起作用,甚至我试图把这个循环放在add()函数中,所以它也应该在这个位置很好,但它也不起作用

// reset all ids
                rewind(ft);
                int id=1;
                while(fread(&p,sizeof(p),1,ft)==1)
                {
                    p.id = id;
                    fwrite(&p,sizeof(p),1,ft);
                    id++;
                }
  

这是我的完整代码,有0个错误和0个警告,除了重置ID的部分之外它工作正常

#include <stdio.h>
#include <stdlib.h>
#include <windows.h>
#include <string.h>
#include <conio.h>

struct address  // nested
{

    char city[30],
         street[30];
    int  flat;

};

struct phonebook  // main
{
    int id;
    char firstName[20],
         lastName[20];
    struct address add;
    long int  phNumber;
    char email[50];

};


// functions ...
void launcher();
void menu();
void add();
void load();
void query();
void Delete();
void modify();
void back();
void scan(char *name);

int main()
{
    system("color 1e");
    printf("Let's start!\n");
    launcher();
    return 0;
}

void launcher()
{
    menu();
}

void back()
{
    menu();
}

void menu()
{

    system("cls");
    printf("\t\t      *********** PhoneBook! *************");

    printf("\n\n\t\t\t\t  <| Menu |>\t\t\n\n");
    printf("\t\t1.Add   \t2.Load   \t3.Query  \n\t\t4.Modify \t5.Delete\t6.Exit\n");

    switch(getch())
    {
    case '1' :
        add();
        break;

    case '2' :
        load();
        break;

    case '3' :
        query();
        break;

    case '4' :
        modify();
        break;

    case '5' :
        Delete();
        break;

    case '6' :
        printf("the program exit successfully");
        exit(0);
        break;

    default:
        system("cls");

        int i;
        for(i=15 ; i>-1 ; i--)
        {
            system("cls");
            printf("\nInvalid key Entered , please enter any key from 1 to 6 only!\n");
            printf("you will back to the main menu automatically in %d seconds",i);
            Sleep(1000);
        }

        menu();


    }

}

void add()
{
    system("cls");
    struct phonebook p; // local define
    FILE *f;
    f= fopen("data","ab+");
    int id=1;

    while(fread(&p,sizeof(p),1,f)==1)
    {
        id++;
    }


    printf("\nFirst Name : ");
    scan(p.firstName);
    printf("\nLast Name : ");
    scan(p.lastName);

    printf("\nEnter the address .. ");
    printf("\n\tCity : ");
    scan(p.add.city);
    printf("\n\tStreet : ");
    scan(p.add.street);
    printf("\n\tFlat : ");
    scanf(" %d",&p.add.flat);

    printf("\nPhone number : ");
    scanf(" %ld",&p.phNumber);
    printf("\nEmail : ");
    scan(p.email);
    p.id=id; // Auto fill
    fwrite(&p,sizeof(p),1,f); // saving the data into a file
    fclose(f);

    puts("\n\n\t\tdata is saved successfully!");
    puts("\t\tEnter any key to back to the main menu");
    getch();
    back();
}

void load()
{
    struct phonebook p;
    system("cls");
    FILE* f;
    f = fopen("data","rb");
    if(f==NULL)
    {
        puts("\n An error occur while opening the file >");

        exit(1);
    }

    while(fread(&p,sizeof(p),1,f)==1)
    {

        printf("\n\n\t\t\t\t  <| loading List |>\t\t\n\n");
        printf("First name : %s\nLast name : %s\nAddress Info ...\nCity : %s\nStreet : %s\nFlat : %d\nPhone Number : %ld\nEmail : %s\nid : %d\n",p.firstName,p.lastName,p.add.city,p.add.street,p.add.flat,p.phNumber,p.email,p.id);

        puts("\t\t * Enter any key to show more *");
        getch();
        system("cls");
    }

    fclose(f);
    puts("\t\tno more data to show !");
    puts("\t\tEnter any key to back to the main menu");
    getch();
    back();




}

void query()
{

    system("cls");
    struct phonebook p;
    FILE* f;
    f = fopen("data","rb");
    if(f==NULL)
    {
        puts("\n An error occur while opening the file >");

        exit(1);
    }

    char name[50];
    int flag=0;
    printf("please enter a name : ");
    scan(name);
    system("cls");
    while(fread(&p,sizeof(p),1,f)==1)
    {

        if(strcmp(name,p.firstName)==0)
        {
            flag++;
            printf("\n[%d] result found\n",flag); // ==> static text
            printf("First name : %s\nLast name : %s\nAddress Info ...\nCity : %s\nStreet : %s\nFlat : %d\nPhone Number : %ld\nEmail : %s\n",p.firstName,p.lastName,p.add.city,p.add.street,p.add.flat,p.phNumber,p.email);

            puts("");
        }
    }

    if(flag == 0)
    {
        puts("file not found");
    }

    fclose(f);
    puts("\t\tEnter any key to back to the main menu");
    getch();
    back();
}

void modify()
{

    system("cls");
    struct phonebook p,s;
    FILE* f;
    f = fopen("data","rb+");
    if(f==NULL)
    {
        puts("\n An error occur while opening the file >");

        exit(1);
    }

    char name[50];
    int flag=0;
    printf("please enter a name : ");
    scan(name);
    system("cls");
    int results[50];
    while(fread(&p,sizeof(p),1,f)==1)
    {

        if(strcmp(name,p.firstName)==0)
        {
            results[flag] = p.id;
            flag++;
            printf("\n\n >> full information about the result No. [%d] :- \n",p.id);
            printf("First name : %s\nLast name : %s\nAddress Info ...\nCity : %s\nStreet : %s\nFlat : %d\nPhone Number : %ld\nEmail : %s\n",p.firstName,p.lastName,p.add.city,p.add.street,p.add.flat,p.phNumber,p.email);

        }
    }

    if(flag == 0)
    {
        puts("file not found");
    }
    else
    {
        int choice,i,found=0;
        int lastResultID = p.id;
        puts("Please enter the Number of the result to confirm your order");
        scanf(" %d",&choice);
        // confirmation
        for(i=0 ; i<flag ;i++){
            if(results[i] == choice){
                found =1;
                break;
            }
        }

        if(found == 0){
            puts("\n Ops! Result not found.\nmaybe you entered a wrong No. OR an Error occurs Try again.");
            Sleep(5000);
            back();
        }else{

            //printf("\n%d\n",lastResultID);
            puts("\n >> Are you want to modify this result ? type (Y) for Yes or (N) for No !");
            char c = getch();
            if( c == 'Y' || c == 'y')
            {
                system("cls");
                printf("\nFirst Name : ");
                scan(s.firstName);
                printf("\nLast Name : ");
                scan(s.lastName);

                printf("\nEnter the address .. ");
                printf("\n\tCity : ");
                scan(s.add.city);
                printf("\n\tStreet : ");
                scan(s.add.street);
                printf("\n\tFlat : ");
                scanf(" %d",&s.add.flat);

                printf("\nPhone number : ");
                scanf(" %ld",&s.phNumber);
                printf("\nEmail : ");
                scan(s.email);
                fseek(f,-sizeof(p)*(lastResultID-choice+1),SEEK_CUR);
                s.id=choice;
                fwrite(&s,sizeof(p),1,f); // saving

                puts("\n\t\tyour data is modified!");
                fclose(f);
                puts("\t\tEnter any key to back to the main menu");
                getch();
                back();


            }
            else
            {

                system("cls");
                puts("nothing change ! , press any key to back to the main menu !");
                getch();
                back();

            }

        }



    }

}

void Delete()
{
    int found =0;
    system("cls");
    struct phonebook p,s;
    FILE* f;
    FILE* ft;
    f = fopen("data","rb");
    ft = fopen("temp","ab+");
    if(f == NULL || ft == NULL)
    {
        puts("\n An error occur while opening the file >");
        perror("fopen() failed");
        exit(1);
    }

    char name[50];
    int flag=0,i;
    int results[50];
    printf("please enter a name : ");
    scan(name);
    system("cls");
    while(fread(&p,sizeof(p),1,f)==1)
    {

        if(strcmp(name,p.firstName)==0)
        {
            results[flag] = p.id;
            flag++;
            printf("\n\n >> full information about the result No. [%d] :- \n",p.id);
            printf("First name : %s\nLast name : %s\nAddress Info ...\nCity : %s\nStreet : %s\nFlat : %d\nPhone Number : %ld\nEmail : %s\n",p.firstName,p.lastName,p.add.city,p.add.street,p.add.flat,p.phNumber,p.email);

        }
    }



    if(flag == 0)
    {
        puts("file not found");
    }
    else{
        puts(" ");
        int choice,check=0;
        puts("please enter the number of the result which you want to delete");
        scanf("  %d",&choice);

        // confirmation
        for(i=0 ; i<flag ;i++){
            if(results[i] == choice){
                check =1;
                break;
            }
        }

        if(check == 0){
            puts("\n Oops! Result not found.\nmaybe you entered a wrong No. OR an Error occurred Try again later.");
            Sleep(3500);
            back();
        }else{

            puts("\n >> Do you want to delete this result ? type (Y) for Yes or (N) for No !");
            char c = getch();
            rewind(f); // reset the pointer
            if( c == 'Y' || c == 'y')
            {
                system("cls");
                while(fread(&p,sizeof(p),1,f)==1)

                {
                    if(choice != p.id)
                        fwrite(&p,sizeof(p),1,ft);
                    if(choice == p.id)
                        found++;
                }

                //perror("fread() failed");



                if(found == 0)
                {
                    puts("An error occurred , please try again");
                    remove("temp");
                    Sleep(3500);
                    back();

                    fclose(f); // ==?
                    fclose(ft); // ==?
                }
                else
                {
                    // reset all ids
                    rewind(ft);
                    int id=1;
                    while(fread(&p,sizeof(p),1,ft)==1)
                    {
                        p.id = id;
                        fwrite(&p,sizeof(p),1,ft);
                        id++;
                    }

                    fclose(f); // ==?
                    fclose(ft); // ==?

                    remove("data");
                    int c = rename("temp","data");
                    puts("file is deleted successfully");

                    if(c != 0)
                        perror("rename() failed"); // handling for rename error



                }

                puts("\t\tEnter any key to back to the main menu");
                getch();
                back();




            }
            else
            {

                system("cls");
                puts("nothing changed ! , press any key to back to the main menu !");
                getch();
                back();

            }


        }


        }


    /*else
    {

        puts("\n >> Are you want to delete this result ? type (Y) for Yes or (N) for No !");
        char c = getch();
        if( c == 'Y' || c == 'y')
        {

            rewind(f);
            while(fread(&p,sizeof(p),1,f)==1)
            {
                if(strcmp(name,p.firstName)!=0)
                    fwrite(&p,sizeof(p),1,ft);
            }

            fclose(f);
            fclose(ft);

            remove("data");
            int c = rename("temp","data");
            puts("file is deleted successfully");

            if(c != 0)
                perror("rename() failed");

            // reset all ids
            int id=1;
            while(fread(&p,sizeof(p),1,f)==1)
            {
                p.id = id;
                fwrite(&p,sizeof(p),1,f);
                id++;
            }
            puts("\t\tEnter any key to back to the main menu");
            getch();
            back();

        }
        else
        {

            system("cls");
            puts("nothing change ! , press any key to back to the main menu !");
            getch();
            back();
        }
    }*/


}

void scan(char *name)
{

    int i=0,j;
    char c,ch;
    do
    {
        c=getch();
        if(c!=8&&c!=13)
        {
            *(name+i)=c;
            putch(c);
            i++;
        }
        if(c==8)
        {
            if(i>0)
            {
                i--;
            }
            // printf("h");
            system("cls");
            for(j=0; j<i; j++)
            {
                ch=*(name+j);
                putch(ch);

            }

        }
    }
    while(c!=13);
    *(name+i)='\0';
}

提前致谢

2 个答案:

答案 0 :(得分:1)

如果使用最高的id + 1而不是计算它们呢?

int id = 1;
while(fread(&p,sizeof(p),1,f)==1)
{
    if (p.id >= id) id = p.id+1;
}

答案 1 :(得分:0)

如果没有干预fread,您无法交错fwritefseek

  

7.21.5.3/7 当使用更新模式打开文件时(&#39; +&#39;作为上述模式参数值列表中的第二个或第三个字符),可以在关联的流上执行输入和输出。但是,如果没有对fflush函数或文件定位函数(fseekfsetposrewind)的干预调用,输出不应直接输入,并且除非输入操作遇到文件结束,否则输入不应直接跟随输出,除非输入操作遇到文件结束。