数据结构 study 4: 学生信息管理 修改信息

数据结构 study 4: 学生信息管理 修改信息

代码如下:

/* c1.h (程序名) */
#include<string.h>
#include<ctype.h>
#include<malloc.h> /* malloc()等 */
#include<limits.h> /* INT_MAX等 */
#include<stdio.h> /* EOF(=^Z或F6),NULL */
#include<stdlib.h> /* atoi() */
#include <sys/io.h> /* eof() */
#include<math.h> /* floor(),ceil(),abs() */

#include<pthread.h> /* exit() */
/* 函数结果状态代码 */
#define TRUE 1
#define FALSE 0
#define OK 1
#define ERROR 0
#define INFEASIBLE -1
/* #define OVERFLOW -2 因为在math.h中已定义OVERFLOW的值为3,故去掉此行 */
typedef int Status; /* Status是函数的类型,其值是函数结果状态代码,如OK等 */
typedef int Boolean; /* Boolean是布尔类型,其值是TRUE或FALSE */

#define NAMELEN 16 /* 姓名最大长度 */     //8
#define CLASSLEN 16 /* 班级名最大长度 */  //4
struct stud /* 记录的结构 */
{
  char name[NAMELEN];
  long num;
  char sex;
  int age;
  char Class[CLASSLEN];
  int health;
};
//{"张立立",790634,'m',17,"计91",2}

FILE *fp;
char sta[3][13]={"健康  ","一般  ","神经衰弱"}; /* 健康状况(3类) */


typedef struct stud ElemType; /* 链表结点元素类型为结构体 */

typedef struct LNode {
    ElemType data;
    struct LNode *next ;
}LNode, *LinkList,*LinkNode ;


int create_list(LinkList *L)
{
    *L = (LinkList)malloc(sizeof(struct LNode));

    if(!(*L)){

        exit(1);
    }

    (*L)->next = NULL ;
    
    return 0 ;
}


/*
  i 从1这个位置开始
*/

int insert_list(LinkList L,int i ,ElemType e)
{
    LinkNode p ; 
    LinkNode s ;
    int j =0 ;

    p = L ;

    if(i <1){

        return -1 ;
    }

    while(p &&(j<i-1))
    {
        p = p->next ;
        j++ ;

    }

    if((!p)||(j<(i-1))){

        return  -1 ;
    }    


    s = (LinkNode)malloc(sizeof(struct LNode));
    if(!s){
        printf("malloc error\n");
        exit(1);
    }

    s->next = NULL;

    s->data = e ;
    s->next = p->next ;

    p->next = s;

    return OK ;
}



void InsertAscend(LinkList L,ElemType e) /* 此函数是由bo2-9.c中的同名函数改写 */
{ /* 按学号非降序插入 */
  LinkList q=L,p=L->next;
  while(p&&e.num>p->data.num)
  {
    q=p;
    p=p->next;
  }
  q->next=(LinkList)malloc(sizeof(struct LNode)); /* 插在q后 */
  q->next->data=e;
  q->next->next=p;
}

Status ReadFromFile(struct stud *e)
{ /* 由fp指定的文件读取结点信息到e */
  int i;
  i=fread(e,sizeof(struct stud),1,fp);
  if(i==1) /* 读取文件成功 */
    return OK;
  else
    return ERROR;
}



void WriteToFile(struct stud e)
{ /* 将结点信息写入fp指定的文件 */
  fwrite(&e,sizeof(struct stud),1,fp);
}


void Print(struct stud e)
{ /* 显示记录e的内容 */
  printf("%-8s %6ld",e.name,e.num);
  if(e.sex=='m')
    printf(" 男");
  else
    printf(" 女");
  printf("%5d  %-4s",e.age,e.Class);
  printf("%13s\n",sta[e.health]);
}



void visit(ElemType data)
{
    printf("%s \n", data.name);
}

int traverse_list(LinkList L,void (*visit)(ElemType ))
{
    LinkNode p = L->next ;

    while(p){

        visit(p->data);

        p = p->next;

        
    }
    
    printf("\n");

    return OK ;    
}

#define N 4 /* student记录的个数 */

Status find_from_num(LinkList L, long num, LinkNode *prev,LinkNode *elem)
{
    LinkNode q = L ;
    int flag = 0 ;

    (*prev) = q;
    q = q->next ;
    
    while(q){
       
        if(q->data.num == num){
            (*elem) = q;
            flag = 1 ;
            break ;
        }       
        
        (*prev) = q ;
        q = q->next ;         
    }

    if(flag == 1){

        return TRUE ;
    }

    return FALSE ;
}

Status delete_elem_num(LinkList L, long num)
{
    LinkNode prev,elem ;

    if(find_from_num(L,num,&prev,&elem)){
        prev->next = elem->next;
        free(elem);
        return TRUE ;
    }

    return FALSE;
}

Status find_from_name(LinkList L, char name[], LinkNode *prev, LinkNode *elem )
{
    LinkNode q ;
    q = L;
    int flag = 0 ;

    (*prev) = q;
    q = q->next ;    
   
    while(q){
        
        if(!strcmp(q->data.name, name)){
            flag = 1 ;
            (*elem) = q ;
            break ;
        }

        (*prev) = q;
        q = q->next ;         
    }

    if(flag == 1){

        return TRUE ;
    }

    return FALSE ;
}

Status delete_elem_name(LinkList L, char name[])
{
    /* 删除表中姓名为name的元素,并返回TRUE;如无此元素,则返回FALSE */    
    LinkNode prev,elem;

    if(find_from_name(L,name,&prev,&elem)){

        prev->next = elem->next;

        free(elem);
        return TRUE;
    }

    return FALSE ;
}


void Modify(ElemType *e)
{ /* 修改结点内容 */
  char s[80];
  Print(*e); /* 显示原内容 */
  printf("请输入待修改项的内容,不修改的项按回车键保持原值:\n");
  printf("请输入姓名(<=%d个字符): ",NAMELEN);
  gets(s);
  if(strlen(s))
    strcpy(e->name,s);
  printf("请输入学号: ");
  gets(s);
  if(strlen(s))
    e->num=atol(s);
  printf("请输入性别(m:男 f:女): ");
  gets(s);
  if(strlen(s))
    e->sex=s[0];
  printf("请输入年龄: ");
  gets(s);
  if(strlen(s))
    e->age=atoi(s);
  printf("请输入班级(<=%d个字符): ",CLASSLEN);
  gets(s);
  if(strlen(s))
    strcpy(e->Class,s);
  printf("请输入健康状况(0:%s 1:%s 2:%s):",sta[0],sta[1],sta[2]);
  gets(s);
  if(strlen(s))
    e->health=atoi(s); /* 修改完毕 */
}




int main()
{
    LinkList L;
    LinkNode q,p;
    int i ;
    int j ;
    ElemType data ;
    int flag =1;
    ElemType e;
    long num;    
    char filename[13] ="table.txt";
    char name[NAMELEN+1];    


    struct stud student_first[N]={
                            {"张三",790621,'m',18,"计91",0},
                            {"李四",790622,'f',20,"计91",1},
                            {"王五",790623,'m',21,"计91",0},
                            {"周杰",790624,'m',17,"计91",2}}; /* 表的初始记录 */

    
    struct stud student[N]={{"王小林",790631,'m',18,"计91",0},
                            {"陈红",790632,'f',20,"计91",1},
                            {"刘建平",790633,'m',21,"计91",0},
                            {"张立立",790634,'m',17,"计91",2}}; /* 表的初始记录 */


    printf("sizeof(\"刘建平\") = %d\n",strlen("刘建平"));
    printf("sizeof(\"计91\") = %d\n",strlen("计91"));  
    printf("Hello World NULL = %d\n",NULL); 
    printf("sizeof(\"神经衰弱\") = %d\n", sizeof("神经衰弱"));
    
    create_list(&L);


    for(i=1;i <= N; i++){

        insert_list(L,i,student_first[i-1]);
    }


    traverse_list(L, visit);    


    
    while(flag)
    {

        printf("\n");
        
        /*
         30(黑色)、31(红色)、32(绿色)、 33(黄色)、
         34(蓝色)、35(洋红)、36(青色)、37(白色)
        */
        
        printf("\033[0;36;40m");
        printf("1:将结构体数组student中的记录按学号非降序(升序)插入链表\n");
        printf("2:将文件中的记录按学号非降序插入链表\n");
        printf("3:键盘输入新记录,并将其按学号非降序插入链表\n");
        printf("4:删除链表中第一个有给定学号的记录\n");
        printf("5:删除链表中第一个有给定姓名的记录\n");
        printf("6:修改链表中第一个有给定学号的记录\n");
        printf("7:修改链表中第一个有给定姓名的记录\n");
        printf("8:查找链表中第一个有给定学号的记录\n");
        printf("9:查找链表中第一个有给定姓名的记录\n");
        printf("10:显示所有记录  \n");
        printf("11:将链表中的所有记录存入文件\n");
        printf("12:结束\n");
        printf("\033[0m");
        printf("\n");
        printf("请选择操作命令: ");
        scanf("%d",&i);
        printf("\n");
        switch(i){

           case 1: for(j=0;j<N;j++)
                     InsertAscend(L,student[j]);
                   break;        
       
           case 2:                
                   if((fp=fopen(filename,"rb"))==NULL)
                   {
                        printf("打开文件失败!\n");
                   }
                   else
                   {
                     while(ReadFromFile(&e)){
                       InsertAscend(L,e);
                     }
                     fclose(fp);
                   }
                   break;    

           case 4: printf("请输入待删除记录的学号: ");
                   scanf("%ld",&num);
                   if(!delete_elem_num(L,num))
                     printf("没有学号为%ld的记录\n",num);
                   break;       

           case 5: printf("请输入待删除记录的姓名: ");
                   scanf("%s",name);
                   if(!delete_elem_name(L,name)){
                     printf("没有姓名为%s的记录\n",name);
                    }
                   break;       
            #if 1        

           case 6: 
                   printf("请输入待修改记录的学号: ");
                   
                   scanf("%ld%*c",&num); /* %*c吃掉回车符 */
           
                   if(!find_from_num(L,num,&p,&q)){
                     printf("没有学号为%ld的记录\n",num);
                   }
                   else
                   {
                     Modify(&q->data);
                     if(q->data.num!=num) /* 学号被修改 */
                     {
                       p->next=q->next; /* 把q所指的结点从L中删除 */
                       InsertAscend(L,q->data); /* 把元素插入L */
                       free(q); /* 删除q */
                     }
                   }
                   break;            
            case 7: printf("请输入待修改记录的姓名: ");
                    scanf("%s%*c",name); /* %*c吃掉回车符 */
                    if(!find_from_name(L,name,&p,&q))
                      printf("没有姓名为%s的记录\n",name);
                    else
                    {
                      num=q->data.num; /* 学号存入num */
                      Modify(&q->data);
                      if(q->data.num!=num) /* 学号被修改 */
                      {
                        p->next=q->next; /* 把q所指的结点从L中删除 */
                        InsertAscend(L,q->data); /* 把元素插入L */
                        free(q); /* 删除q */
                      }
                    }
                    break;
            #endif 
            
            case 10:
                   printf("姓名    学号 性别 年龄 班级 健康状况\n");
                   traverse_list(L,Print);
                   break;               
            case 11:                
                    if((fp=fopen(filename,"wb"))==NULL){
                      printf("打开文件失败!\n");
                    }
                    else{
                      traverse_list(L,WriteToFile);
                    }
                    fclose(fp);
                    break;
                    
            case 12:
                flag = 0 ;
                break ;
        }    
    }
    
}



在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值