• c博客06-结构体&文件


    1.本章学习总结

    1.1 学习内容总结

    思维导图.

    结构体.

    结构体的创建、定义、初始化、引用、排序、指针.

    创建结构体

    struct 结构体名称
    {
        定义结构体成员1;
        定义结构体成员2;
        ·
        ·
        ·
    };
    
    typedef struct
    {
        定义结构体成员1;
        定义结构体成员2;
        ·
        ·
        ·
    }结构体名称;
    

    结构体的定义
    struct 结构体名称 结构体变量
    例如:
    struct student name;
    struct student *p;
    struct student menber[10];

    结构体的初始化
    结构体和数组一样都禁止对整体赋值。结构体的初始化要根据创建的结构体成员的类型来逐一赋值

    struct student
    {
        char op;
        int number;
        char name[10];
    };
    struct student menber = {'+',56,"hjx"};
    

    结构体变量的引用

    • 结构体成员运算符 '.'
    • 结构体指针变量访问其所指向结构体成员运算符 '->' (中间不要加空格)

    结构体数组排序做法
    结构体的排序,不是对结构体整体排序,而是针对结构体中的某个成员进行排序,与前面数组排序类似.

    struct student
    {
        char number;
        char name[10];
        int score;
    };
    struct student menber[10];
    输入n个人数,对结构体数组进行相应的赋值
    对结构体成员中的score进行排序
    for(int i=0 to n do i++)
        for (int j=0 to n-i do j++)
            if(menber[j].score>menber[j+1].score)
                交换整个结构体
            end if
        end for
    end for
    

    结构体指针
    创建一个结构体;
    定义一个结构体指针
    引用结构体指针: p->结构体成员 ;(*p) .结构体成员

    文件.

    文件的处理流程.

    定义文件指针
    FILE *fp;

    打开文件

    fp=fopen("xxx.txt","op");    //前面为文件名称,后面是对文件进行的操作
    if(fp==NULL) //如果没有成功打开文件,系统应该给一点提示
        printf("open file error!")
        exit(0); //让程序退出这个程序
    

    关闭文件

    if (fclose(fp)) //如果没有成功关闭文件,系统给予提示
        printf("sorry , close error!
    ");
        exit(0); //强制退出程序
    

    文件读取、写入的函数

    字符读写函数:fgetc和fputc
    字符串读写函数:fgets和fputs
    数据块读写函数:freed 和 fwrite
    格式化读写函数:fscanf 和 fprinf
    

    共用体.

    共用体的含义、声明与定义、与共用体的区别.

    含义
    使用同一段内存单元存放不同类型的变量,或者说使几个不同的变量共享同一段内存的结构,称为“共用体”类型的结构
    共用体的声明、定义

    union Data{
        int n;
        char ch;
        double f;
    };
    union Data a, b, c;
    

    结构体与共用体的区别

    • 结构体的各个成员会占用不同的内存,互相之间没有影响;而共用体的所有成员占用同一段内存,修改一个成员会影响其余所有成员。
    • 结构体占用的内存大于等于所有成员占用的内存的总和(成员之间可能会存在缝隙),共用体占用的内存等于最长的成员占用的内存。
    • 共用体使用了内存覆盖技术,同一时刻只能保存一个成员的值,如果对新的成员赋值,就会把原来成员的值覆盖掉。

    枚举类型.

    枚举的含义、定义、数值问题.

    含义
    所谓“枚举”就是把可能的值一一列举出来,变量的值只限于列举出来的值的范围内。
    枚举的定义

    enum week
    { 
    Mon, Tues, Wed, Thurs, Fri, Sat, Sun 
    };
    

    枚举的数值问题
    枚举值默认从 0 开始,往后逐个加 1。枚举可以给指定成员赋值,后面的成员就是在该数值上逐个加1;
    枚举的成员是常量,不能在程序中对其进行赋值操作,只能将枚举成员的值赋给其他变量

    1.2 本章学习体会

    学习感受.

    结构体的应用熟能生巧,并且结构体运用起来很方便。结构体比数组最优秀的地方在于,它可以直接将整个结构体进行交换,就是说,结构体的每一个成员可以用另一个结构体来赋值,这样的操作比数组方便灵活使用。两个数组不能直接赋值,但是结构体可以。只要掌握了结构体的声明、定义,就可以让结构体在我们的键盘下生出花来。但是文件不行,尽管文件中有的部分也是固定的,或许只要记住那些打开文件、关闭文件的基本代码,其他的和平常差不多,文件使用起来没有想象中的轻松,它其中很多的语法点很容易忽略就会导致出错,还有那几个文件的读写函数,要灵活应用,否则一不小心就出错了。文件就是从扎堆写程序走向模块化程序,懂得分块处理程序,分功能封装函数,走工程化道路。处理文件时,一个处理不好可能就会让文件里面储存的东西变得乱七八糟,所以在这方面的处理还是要注意一些。调试文件代码时,也要很细心,因为有的时候不是整体代码的问题,只是其中定义的问题,就要很认真耐心的去找错了。文件这方面,我还没有懂的其中的意义,只是把函数分装在不同的文件里面。之后我会去慢慢改善,让文件的功能不只是分装......

    代码量.

    2.综合作业--“我爱成语”

    2.1.文件介绍

    头文件介绍.

    函数实现文件介绍.

    main.cpp.

    功能介绍

    菜单函数,展示菜单
    输入账户、密码的界面
    判断用户输入的是否与文件里面的相匹配,只有两次输入的机会,如果两次用户都输入错误,就会被强制退出系统。
    根据用户的选择进入那个搜索成语或者答题成语
    两种选择进入循环,如果用户选择中途退出就输入用户退出程序的时间以及其获得的分数
    退出程序
    

    代码截图

    readfile.cpp.

    功能介绍

    打开成语文档,将成语、注释储存到全局变量file中
    

    代码截图

    questionAndcheckanswer.cpp

    功能介绍

    产生三个随机数linenumber,num1,num2
    linenumber控制出题的第几行成语
    num1,num2控制输入成语的第几个字
    for循环空格空格输出
    输出较前的一个字
    for循环控制空格输出
    输出较后的一个字
    for循环控制空格输出
    
    提示用户补充成语
    对用户输入的汉字进行判断,正确加5分
    输出这一个成语以及对应的成语解释
    

    代码截图

    randomnumber.cpp.

    功能介绍
    根据传入的参数不同,产生不同范围的随机数
    代码截图

    choice.cpp.

    功能介绍

    选择函数:统计用户的选择,查找成语函数是否需要,做题函数是否需要
    搜索成语函数:将成语文本中的成语输出,只输出成语,不输出成语的解释
    退出函数:询问用户是否要退出程序
    

    代码截图

    loading.cpp.

    功能介绍

    菜单函数:界面友好,展示菜单,给用户提供选择
    登录函数:用户输入账户、密码的界面,并且保护用户的密码,将用户输入的密码用*代替
    检查用户输入的账户与密码函数:将用户输入的账户密码连起来,与文档的每一行进行比对,返回对应的数组,正确返回1,错误返回0
    读取时间函数:读取用户退出程序所对应的时间
    

    代码截图

    2.2运行结果

    1.登录界面

    2.游戏界面

    3.时间界面

    4.查找成语界面

    2.3大作业总结

    1.碰到问题及解决办法

    Q1:全局变量file有问题,不用static程序会运行错误,使用之后,file数组只在第一次使用这个变量的函数里面才有值,别的函数使用它时为空。
    A1:定义改为extern char file[60][160]这样定义,并在main函数的外面写一遍这个定义,这样就可以输出这里面储存的字符
    Q2:查找函数里面,两个for循环那里,运行的时候报错,读取位置冲突
    A2:file数组最后一个字符赋特殊值,第一层for循环的时候,判断file[i][0]是否为那个特殊值,是的话就退出循环,不是就进行下面的操作。当时file数组是放大的,并没有考虑到多余的部分的问题,所以导致程序运行出错,乱码。
    Q3:写完那个打开文件的函数时,一运行就报错
    A3:对于不正常的打开和关闭可以使用exit(0),而我之前使用了return 0;因为函数是无返回的,所以正确的使用应该是return;
    Q4:对比文档中的账号和密码与用户输入的账户与密码的函数出现了正确输入却不能成功进入系统的问题
    A4:我使用的方法是将用户输入的账户连接一个空格在连接密码在连接一个换行作为一个整体字符串与文档中的一行字符串进行比较,明明老师上课就是这样讲的,可是它一直出错,显示不匹配,然后我灵光一闪,把那个连接换行的代码注释掉发现这样才是正确的
    Q5:搜索函数与中途退出函数链接不当,导致中途退出函数没有发挥作用
    A5:在搜索函数与中途退出函数中间加一个getchar(),吸收用户输入的想搜索的成语之后的那个换行
    Q6:输入成语以及其注释的时候中文乱码了
    A6:将成语文档的格式改为ANSI
    

    2.小结

    • 有了上次写大作业的经验,先分框架构思整个代码,一部分一部分的写,而且写完一个部分就应该运行,不能等到全部写完再去运行,到时候程序出错是很难去调试的,所以我们每每写完一部分就要确保它能够运行成功,这样后面即使是改错也可以减少精力和时间。本次大作业,对于结构体的运用以及文件的初步使用,有了新一步认识。因为是比较不熟悉的内容,在操作性上,比之前要陌生很多,还是归结于使用次数不够多,所以才比较欠缺一些。这次的大作业让我对于程序的结构有了更深刻的感悟,无论是什么,结构都是很重要的,一项工程想要很好的去完成它,结构清晰是必不可少的,也只有分清工程的结构以及每一个part才能高效的完成一项工作,现在不是缺少完成工作的人,欠缺的是在较短时间内完美的结束工作的人才。所以文件的区块化就显得尤为重要。
    • 每次写大作业,都有很多不一样的感触,从之前的bug满屏飞到现在能完成一个成语出题系统,除了学习能力上有所增进,在心中对C语言有了一股不一样的感觉。之前没有接触到这一方面,觉得自己肯定不能做出任何关于编程的东西,想当初我的第一个HELLO,WORLD!的程序花费了半个小时才写出来。尽管现在的代码量或者大作业,在大佬眼中不值一提,可是每个人都是这样经历过来的呀,从来都没有天才,是自己的汗水造就了自己,山上的人不要看不起上山的人,每一个人都有登山的可能。C语言真的很神奇,它像是一种魔术,创造了一个类虚拟世界,让你在里面尽情的撒欢,描述你的满腹委屈,当你的伤痛被C语言抚平的时候,那才是我们码农的巅峰时刻,让C在我们的世界狂欢!
  • 相关阅读:
    qt预览的UI界面和实际运行出来的界面分辨率不一样
    QByteArray转QString 例如 0x45 转成 “45”
    QML访问C++成员函数报错:TypeError: Property 'showHome' of object [object Object] is not a function
    Qt生成二维码
    Android解析编译之后的所有文件(so,dex,xml,arsc)格式
    Android逆向之旅---解析编译之后的Dex文件格式
    Android逆向之旅---解析编译之后的Resource.arsc文件格式
    Android逆向之旅---解析编译之后的AndroidManifest文件格式
    Android签名机制之---签名验证过程详解
    Android签名机制之---签名过程详解
  • 原文地址:https://www.cnblogs.com/springxinxin/p/11985602.html
Copyright © 2020-2023  润新知