c语言怎么用文件保存和读取 结构体数组

Python018

c语言怎么用文件保存和读取 结构体数组,第1张

#include <stdio.h>

int main()

{

struct test {

int a

char s[10]

double d

} tr[3] , tw[3] ={

{1,"hello1" , 100 },

{2,"hello2" , 90},

{3,"hello3", 200}

} //定义一个结构体数组

FILE *fp

fp=fopen("struct.dat" , "wb" )

if ( fp == NULL )

return -1

fwrite( (char*)tw , sizeof(struct test), 3 , fp )//将数组写入文件

fclose(fp)

//以上完成写操作

fp=fopen("struct.dat" , "rb" )

if ( fp == NULL )

return -1

fread( (char*)tr , sizeof(struct test), 3 , fp )//从文件中读三个结构体的数据,也可以一个一个的读

fclose(fp)

//输出读到的数据

{

int i

for(i=0i<3i++ )

printf("%d %s %lf\n" , tr[i].a , tr[i].s, tr[i].d )

}

return 0

}

#include "stdio.h"

#include "stdlib.h"

#include "string.h"

int shoudsave=0

char dir[15]

struct member

{

char num[5]//编号

char name[15]

char sex[1]

float spercent

float zpercent

float xpercent

float jiangjin

float totle

float ave

}//一个结构体

typedef struct node

{

struct member data//指向结构体的结构体

struct node *next

}Node,*Link

void explain()

{printf("=============================关于此程序的操作说明==============================\n")

printf("===1>:员工每旬应该完成量为33.3个百分点,输入只输数字部分。\n")

printf("===2>:员工每月应该完成量完成量为100个百分点。\n")

printf("===3>:员工奖金按其超额总应该完成量(即百分之百)的多少计算。\n")

printf("===4>:奖金=(总完成比-1)*1000。\n")

printf("===5>:员工底金为1000元。\n")

printf("===6>:逻辑删除资料必须在已经保存了先前记录的基础上方可进行。\n")

printf("===7>:进行逻辑删除资料后如果保存即变为物理删除。\n")

printf("===8>:本程序在c++环境中完成,程序文件扩展名为.c。\n")

}

void menu() //菜单

{

printf("********************************************************************************")

printf("\t1获取说明信息\t\t\t\t\t 2输入员工资料\n")

printf("\t3删除员工资料\t\t\t\t\t 4查询员工资料\n")

printf("\t5修改员工资料\t\t\t\t\t 6显示员工资料\n")

printf("\t7统计员工业绩\t\t\t\t\t 8排序员工实发工资\n")

printf("\t9保存员工资料\t\t\t\t\t10逻辑删除员工资料\n")

printf("\t0退出系统\n")

printf("********************************************************************************\n")

}

void printc() // 本函数用于输出中文

{

printf("编号 姓名性别 总完成比 旬平均 基本工资 奖金 工资总额 \n")

}

void printe(Node *p)//本函数用于输出英文

{

printf("%-5s%-10s%-4s%6.1f %6.1f %6.1f %6.1f %6.1f\n",p->data.num,p->data.name,p->data.sex,p->data.totle,p->data.ave,1000.0,p->data.jiangjin,1000+p->data.jiangjin)

}

void printstart()

{

printf("-----------------------------------------------------------------------\n")

}

void Wrong() //如果错误

{

printf("\n=====>提示:输入错误!\n")

}

void Nofind() //如果没找到

{

printf("\n=====>提示:没有找到该员工!\n")

}

Node* Locate(Link l,char findmess[],char nameornum[]) //该函数用于定位连表中符合要求的接点,并返回该指针

{

Node *r

if(strcmp(nameornum,"num")==0) //按编号查询

{

r=l->next

while(r!=NULL)

{

if(strcmp(r->data.num,findmess)==0)

return r

r=r->next

}

}

else if(strcmp(nameornum,"name")==0) //按姓名查询

{

r=l->next

while(r!=NULL)

{

if(strcmp(r->data.name,findmess)==0)

return r

r=r->next

}

}

return 0

}

void Add(Link l) //增加员工

{

Node *p,*r,*s

char num[10]

r=l

s=l->next

while(r->next!=NULL)

r=r->next//将指针置于最末尾

//while(1)

{

printf("请你输入编号(以'0'返回上一级菜单:)")

fflush(stdin)

gets(num)

if(strcmp(num,"0")==0)return//比较判断是否返回

//break

}

while(s)

{

if(strcmp(s->data.num,num)==0) //比较判断是否重复

{

printf("=====>提示:编号为'%s'的员工已经存在,若要修改请你选择'4 修改'!\n",num)

printstart()

printc()

printe(s)

printstart()

printf("\n")

return

}

s=s->next

}

p=(Node *)malloc(sizeof(Node))//开辟一个指定大小的存储空间

strcpy(p->data.num,num)

printf("请您输入姓名:")

scanf("%s",p->data.name)

getchar()

printf("请您输入性别(m/f):")

scanf("%s",p->data.sex)

getchar()

printf("请您输入上旬完成(百分比):")

scanf("%f",&p->data.spercent)

getchar()

printf("请您输入中旬完成(百分比):")

scanf("%f",&p->data.zpercent)

getchar()

printf("请您输入下旬完成(百分比):")

scanf("%f",&p->data.xpercent)

getchar()

p->data.totle=p->data.spercent+p->data.zpercent+p->data.xpercent

p->data.ave=p->data.totle / 3

if(p->data.totle<100)

else p->data.jiangjin=(p->data.totle-100)*10

//信息输入已经完成

p->next=NULL

r->next=p

r=p

shoudsave=1

}

void Search(Link l) //查询员工

{

int sel

char findmess[20]

Node *p

if(!l->next)

{

printf("\n=====>提示:没有资料可以查询!\n")

return

}

printf("\n=====>1按编号查找\n======>2按姓名查找\n======>3返回上一级菜单\n")

scanf("%d",&sel)

if(sel==3)

if(sel==1)//编号

{

printf("请您输入要查找的编号:")

scanf("%s",findmess)

p=Locate(l,findmess,"num")//定位链表中符合要求的节点

if(p)

{

printf("\t\t\t查找结果(完成单位:个百分比)\n")

printstart()

printc()

printe(p)

printstart()

}

else

Nofind()

}

else

if(sel==2) //姓名

{

printf("请您输入要查找的姓名:")

scanf("%s",findmess)

p=Locate(l,findmess,"name")//定位链表中符合要求的节点

if(p)

{

printf("\t\t\t\t查找结果\n")

printstart()

printc()

printe(p)

printstart()

}

else

Nofind()

}

else

Wrong()

}

void Del(Link l) //物理删除

{

int sel

Node *p,*r

char findmess[20]

if(!l->next)

{

printf("\n=====>提示:没有资料可以删除!\n")

return

}

printf("\n=====>1按编号删除\n=====>2按姓名删除\n======>3返回上一级菜单\n")

scanf("%d",&sel)

if(sel==3)

if(sel==1)

{

printf("请你输入要删除的编号:")

scanf("%s",findmess)

p=Locate(l,findmess,"num")//定位链表中符合要求的节点

if(p)

{

r=l

while(r->next!=p)

r=r->next

r->next=p->next

free(p)

printf("\n=====>提示:该员工已经成功删除!\n")

shoudsave=1

}

else

Nofind()

}

else if(sel==2)

{

printf("请你输入要删除的姓名:")

scanf("%s",findmess)

p=Locate(l,findmess,"name")//定位链表中符合要求的节点

if(p)

{

r=l

while(r->next!=p)

r=r->next

r->next=p->next

free(p)

printf("\n=====>提示:该员工已经成功删除!\n")

shoudsave=1

}

else

Nofind()

}

else

Wrong()

}

void Ndel(Link l) //逻辑删除

{

int sel

Node *p,*r

char findmess[20]

if(shoudsave==1)

{printf("\n=====>提示:请您先保存已输入的记录,再进行逻辑删除。要物理删除请按3。\n")

return

}

if(!l->next)

{

printf("\n=====>提示:没有资料可以删除!\n")

return

}

printf("\n=====>1按编号删除\n=====>2按姓名删除\n======>3返回上一级菜单\n")

scanf("%d",&sel)

if(sel==3)

if(sel==1)

{

printf("请你输入要删除的编号:")

scanf("%s",findmess)

p=Locate(l,findmess,"num")//定位链表中符合要求的节点

if(p)

{

r=l

while(r->next!=p)

r=r->next

r->next=p->next

free(p)

printf("\n=====>提示:该员工已经成功删除!\n")

shoudsave=0

}

else

Nofind()

}

else if(sel==2)

{

printf("请你输入要删除的姓名:")

scanf("%s",findmess)

p=Locate(l,findmess,"name")//定位链表中符合要求的节点

if(p)

{

r=l

while(r->next!=p)

r=r->next

r->next=p->next

free(p)

printf("\n=====>提示:该员工已经成功删除!\n")

shoudsave=0

}

else

Nofind()

}

else

Wrong()

}

void Modify(Link l) //修改员工资料

{ int choose

Node *p

char findmess[20]

if(!l->next)

{

printf("\n=====>提示:没有资料可以修改!\n")

return

}

printf("请你输入要修改的员工编号(以0返回上一级菜单):")

scanf("%s",findmess)

if(strcmp(findmess,"0")==0) return

p=Locate(l,findmess,"num")//定位链表中符合要求的节点

if(p)

{printf("=========>1:修改员工编号\n")

printf("=========>2:修改员工姓名\n")

printf("=========>3:修改员工性别\n")

printf("=========>4:修改员工上旬完成百分比\n")

printf("=========>5:修改员工中旬完成百分比\n")

printf("=========>6:修改员工下旬完成百分比\n")

printf("\n-------请你输入要修改的员工条目:")

scanf("%d",&choose)

switch(choose)

{ case 1: printf("请你输入新编号(原来是%s):",p->data.num)

scanf("%s",p->data.num)break

case 2: printf("请你输入新姓名(原来是%s):",p->data.name)

scanf("%s",p->data.name)

getchar()break

case 3: printf("请你输入新性别(原来是%s):",p->data.sex)

scanf("%s",p->data.sex)break

case 4: printf("请你输入新的上旬完成百分比(原来是%5.2f ):",p->data.spercent)

scanf("%f",&p->data.spercent)

getchar()

p->data.totle=p->data.spercent+p->data.zpercent+p->data.xpercent

p->data.ave=p->data.totle / 3

if(p->data.totle<100)

else p->data.jiangjin=(p->data.totle-100)*10

break

case 5: printf("请你输入新的中旬完成百分比(原来是%5.2f ):",p->data.zpercent)

scanf("%f",&p->data.zpercent)

getchar()

p->data.totle=p->data.spercent+p->data.zpercent+p->data.xpercent

p->data.ave=p->data.totle / 3

if(p->data.totle<100)

else p->data.jiangjin=(p->data.totle-100)*10

break

case 6: printf("请你输入新的下旬完成百分比(原来是%5.2f ):",p->data.xpercent)

p->data.totle=p->data.spercent+p->data.zpercent+p->data.xpercent

p->data.ave=p->data.totle / 3

if(p->data.totle<100)

else p->data.jiangjin=(p->data.totle-100)*10

break

default: Wrong()return

}

printf("\n=====>提示:资料修改成功!\n")

shoudsave=1

}

else

Nofind()

}

void Disp(Link l) //显示员工资料

{

int count=0

Node *p

p=l->next

if(!p)

{

printf("\n=====>提示:没有资料可以显示!\n")

return

}

printf("\t\t\t显示结果(完成单位:个百分比)\n")

printstart()

printc()

printf("\n")

while(p)

{

printe(p)

p=p->next

}

printstart()

printf("\n")

}

void Tongji(Link l) //统计员工资料

{

Node *pz,*px,*ps,*pt,*pa,*pj//用于指向分数最高的接点

Node *r=l->next

if(!r)

{

printf("\n=====>提示:没有资料可以统计!\n")

return

}

ps=pz=px=pt=pa=pj=r

while(r!=NULL)

{

if(r->data.spercent>=ps->data.spercent)

ps=r

if(r->data.zpercent>=pz->data.zpercent)

pz=r

if(r->data.xpercent>=px->data.xpercent)

px=r

if(r->data.totle>=pt->data.totle)

pt=r

if(r->data.ave>=pa->data.ave)

pa=r

if(r->data.jiangjin>=pa->data.jiangjin)

pj=r

r=r->next

}

printf("-----------------统计结果--------------------------\n")

printf("月总完成最高者:\t%s %5.2f个百分比\n",pt->data.name,pt->data.totle)

printf("平均完成最高者:\t%s %5.2f个百分比\n",pa->data.name,pa->data.ave)

printf("上旬完成最高者:\t%s %5.2f个百分比\n",ps->data.name,ps->data.spercent)

printf("中旬完成最高者:\t%s %5.2f个百分比\n",pz->data.name,pz->data.zpercent)

printf("下旬完成最高者:\t%s %5.2f个百分比\n",px->data.name,px->data.xpercent)

printf(" 奖金最高者:\t%s %5.2f元\n",pj->data.name,pj->data.jiangjin)

printstart()

}

void Sort(Link l)//按员工实发工资(即其完成额大小)排序

{int m

Link ll

Node *p,*rr,*s

ll=(Link)malloc(sizeof(Node))//用于做新的链表

ll->next=NULL

if(l->next==NULL)

{

printf("\n=====>提示:没有资料可以排序!\n")

return

}

p=l->next

while(p)

{

s=(Node*)malloc(sizeof(Node))//新建接点用于保存信息

s->data=p->data

s->next=NULL

rr=ll

while(rr->next!=NULL &&rr->next->data.totle>=p->data.totle)

rr=rr->next

if(rr->next==NULL)

rr->next=s

else

{

s->next=rr->next

rr->next=s

}

p=p->next

}

free(l)

l->next=ll->next

printf("\n=====>提示:排序已经完成!\n")

for(m=1rr->next!=NULLm++)

{rr=rr->next

printf("\n第%d名",m)printf("\n编号:%s",rr->data.num)printf(" 姓名:%s",rr->data.name)printf(" 性别:%s",rr->data.sex)printf(" 工资总额:%5.2f+1000\n",rr->data.ave)

}

}

void Save(Link l) //保存已经输入的员工资料

{

FILE* fp

Node *p

int flag=1,count=0

fp=fopen(dir,"wb")

if(fp==NULL)

{

printf("\n=====>提示:重新打开文件时发生错误!\n")

exit(1)

}

p=l->next

while(p)

{

if(fwrite(p,sizeof(Node),1,fp)==1)

{

p=p->next

count++

}

else

{

flag=0

break

}

}

if(flag)

{

printf("\n=====>提示:文件保存成功.(有%d条记录已经保存.)\n",count)

shoudsave=0

}

fclose(fp)

}

void main() //主函数Main

{

Link l//连表

FILE *fp//文件指针

int sel

char ch

char jian

int count=0

//char mima[10]

Node *p,*r

printf("\t\t\t员工工资管理系统\n\t\t\t\t------电子1班\n\t\t\t\t\t孙大光\n")

l=(Node*)malloc(sizeof(Node))

l->next=NULL

r=l

fp=fopen("C:\\member1","rb")//打开文件夹

if(fp==NULL)

{

printf("\n=====>提示:文件还不存在,是否创建?(y/n)\n")

scanf("%c",&jian)

if(jian=='y'||jian=='Y')

{printf("输入路径:")

scanf("%s",dir)

fp=fopen(dir,"wb")}

else exit(0)

if(fp)

{printf("\n=====>提示:文件已经打开,正在导入记录......\n")

printf("\n=====>提示:记录导入完毕,共导入%d条记录.\n",0) }

}

else

{while(!feof(fp))

{

p=(Node*)malloc(sizeof(Node))//开辟一个指定大小的存储空间

if(fread(p,sizeof(Node),1,fp)) //将文件的内容放入接点中

{

p->next=NULL

r->next=p

r=p//将该接点挂入连中

count++

}

}

fclose(fp)//关闭文件

printf("\n=====>提示:记录导入完毕,共导入%d条记录.\n",count)

}

while(1)

{

menu()

printf("请你选择操作:")

scanf("%d",&sel)

if(sel==0)

{

if(shoudsave==1)

{ getchar()

printf("\n=====>提示:资料已经改动,是否将改动保存到文件中(y/n)?\n")

scanf("%c",&ch)

if(ch=='y'||ch=='Y')

Save(l)

}

printf("\n=====>您已经退出系统,谢谢您的使用,再见!\n")

break

}

switch(sel)

{

case 1:explain()break//操作说明

case 2:Add(l)break//增加员工资料

case 3:Del(l)break//删除员工资料

case 4:Search(l)break//查询员工资料

case 5:Modify(l)break//修改员工资料

case 6:Disp(l)break//显示员工资料

case 7:Tongji(l)break//统计员工资料

case 8:Sort(l)break//排序员工资料

case 9:Save(l)break//保存员工资料

case 10:Ndel(l)break//逻辑删除员工资料

default: Wrong()getchar()break

write(&cus[i],sizeof(structclient),1,fp)是什么意思答:c语言把一个结构体数组写入文件分三步:1、以二进制写方式(wb)打开文件2、调用写入函数fwrite()将结构体数据写入文件3、关闭文件指针相应的,读文件也要与之匹配:1、以二进制读方式(rb)打开文件2、调用读文件函数fread()读取文件中的数据.