C语言上机复习(一)文件操作

C语言—文件操作

1.1 fgetc() + fputc(): 以 字符 形式存取数据定义文件指针

#define _CRT_SECURE_NO_WARNINGS
#include <cstdio>
#include <cstdlib>
using namespace std;

/*
文件结束标志: EOF --- feof()

读写文件:
fgetc: file get char 以字符形式获取
fputc: file put char 以字符形式写到文件

*/
int main()
{
    //定义文件指针
    FILE *fp;
    //打开文件
    fp = fopen("fopen_01.txt", "w+");

    //判断文件打开是否成功
    if (!fp) {
        printf("打开文件失败\n");
        exit(0);
    }

    //写的方式: 自己移动
    fputc('a', fp);
    fputc('b', fp);
    fputc('c', fp);

    //打开文件
    fclose(fp);


    //只读文件
    FILE *read = fopen("fopen_01.txt", "r");

    if (!read) {
        printf("打开文件失败\n");
        exit(0);
    }

    //读文件
    //fgetc(): 放回int值, 以字符形式获取
    int ch = fgetc(read);
    while (ch != EOF)
    {
        putchar(ch);        //打印字符到命令行
        ch = fgetc(read);
    }

    printf("\n");

    fclose(read);

    return 0;

}

2.2 fgets() + fputs(): 以 字符串 形式存取数据

#define _CRT_SECURE_NO_WARNINGS
#include <cstdlib>
#include <cstdio>
using namespace std;

/*

int fputs(char *str, FILE *fp);
char* fgets(char *str, int n, FILE *fp);

*/
int main()
{
    FILE *fp = fopen("fgets_fputs_02.txt", "w+");

    if (!fp) {
        printf("打开文件失败");
        exit(1);
    }

    //写的方式: 自己移动
    int isok = fputs("Douzi is cute\n I love china!\n who are you?", fp);
    //返回非负值,表示成功
    printf("返回非负值表示成功: %d\n", isok);
    
    fclose(fp);

    FILE *read = fopen("fgets_fputs_02.txt", "r");
    if (!read) {
        printf("打开文件失败\n");
        exit(1);
    }

    //读文件
    char str[50] = "";
    //设置读取的长度
     while (fgets(str, 50, read))
    {
        puts(str);
    }
    //puts(str);

    fclose(read);

    return 0;

}

2.3 fread() + fwrite(): 以 二进制 形式存取数据

2.3.1 结构体数据

#define _CRT_SECURE_NO_WARNINGS
#include <cstdio>
#include <iostream>
#include <cstdlib>
#include <cstring>
using namespace std;

/*
//以二进制形式存储数据
int fwrite(void *buffer,unsigned size, unsigned count, FILE * fp)

//以什么方式写进去就以什么方式读出 !!
int fread(void *buffer,unsigned size, unsigned count, FILE * fp)
*/

struct student
{
    char name[20];
    int age;
    double num;
}mystudent;

int main()
{
    //写文件
    FILE *fp = fopen("fread_fwrite_03.bat", "wb");
    if (fp == NULL) {
        printf("打开失败\n");
        exit(1);
    }

    while (true)
    {
        printf("输入姓名-年龄-成绩:\n");
        scanf("%s%d%lf", &mystudent.name, &mystudent.age, &mystudent.num);
        //参数: 源起始位置, 写多少(字节), 写的次数, 目的地
        //     &mystudent, sizeof(struct student), 1, fp
        fwrite(&mystudent, sizeof(struct student), 1, fp);
        printf("是否继续?(Y/N)");

        //清除缓冲区
        //否则下面的字符无法输入,因为上面输入按下回车,"回车"会被下面的getchar()吃掉,而无法自己输入
        fflush(stdin);
        int ch = getchar();
        if (ch == 'N' || ch == 'n') {
            break;
        }
    }
    fclose(fp);

    //读取文件
    FILE *read = fopen("fread_fwrite_03.bat", "rb");
    if (!read) {
        printf("文件打开失败\n");
        exit(1);
    }

    //以二进制形式读取
    while (fread(&mystudent, sizeof(struct student), 1, read) > 0) {
        printf("姓名\t年龄\t成绩:\n");
        printf("%s\t%d\t%.2f\n", mystudent.name, mystudent.age, mystudent.num);
    }    

    fclose(read);

    return 0;

}

2.3.2 结构体数组

#define _CRT_SECURE_NO_WARNINGS
#include <cstdio>
#include <iostream>
#include <cstdlib>
#include <cstring>
using namespace std;

/*
//以二进制形式存储数据
int fwrite(void *buffer,unsigned size, unsigned count, FILE * fp)

//以什么方式写进去就以什么方式读出 !!
int fread(void *buffer,unsigned size, unsigned count, FILE * fp):
    count: 知道有多少数据可以读取

*/

const int maxn = 1024 + 10;
struct student
{
    char name[20];
    int age;
    double num;
}stus[maxn];

int main()
{
    ////写文件
    FILE *fp = fopen("fread_fwrite_03.bat", "wb");
    if (fp == NULL) {
        printf("打开失败\n");
        exit(1);
    }


    int cnt;
    scanf("%d", &cnt);
    for (int i = 0; i < cnt; i++)
    {
        printf("输入姓名-年龄-成绩:\n");
        scanf("%s%d%lf", &stus[i].name, &stus[i].age, &stus[i].num);        
        
        //清除缓冲区
        //否则下面的字符无法输入,因为上面输入按下回车,"回车"会被下面的getchar()吃掉,而无法自己输入
        fflush(stdin);
    }
    //参数: 源起始位置, 写多少(字节), 写的次数, 目的地
    //     stus, sizeof(struct student), cnt, fp
    fwrite(stus, sizeof(struct student), cnt, fp);

    fclose(fp);

    //读取文件
    FILE *read = fopen("fread_fwrite_03.bat", "rb");
    if (!read) {
        printf("文件打开失败\n");
        exit(1);
    }

    student read_demo[maxn];
    fread(read_demo, sizeof(struct student), cnt, read);
    
    for (int i = 0; i < cnt; i++){
        printf("姓名\t年龄\t成绩:\n");
        printf("%s\t%d\t%.2f\n", read_demo[i].name, read_demo[i].age, read_demo[i].num);
    }



    return 0;

}

 

2.4 fprintf() + fscanf():模式化读写文件数据

#define _CRT_SECURE_NO_WARNINGS
#include <cstdio>
#include <cstdlib>
using namespace std;

/*
//printf: 多了指定位置
//参数: 指定位置, 与printf一样的格式化【类似%d这样】, 参数列表
int fscanf(FILE *fp, char *format, arg_list);
int fprintf(FILE *fp, char *format, arg_list);
    stdin:  标准输入 -- 键盘输入
    stdout: 标准输出 -- 屏幕输出
    FILE *: 自定义输入输出​
*/

const int maxn = 20;
struct Student
{
    char name[maxn];
    int age;
    double score;
} mystu, stu[maxn];


int main()
{
    //写文件
    ////标准输入输出
    //printf("请输入姓名,年龄,成绩: \n");
    //fscanf(stdin, "%s%d%lf", mystu.name, &mystu.age, &mystu.score);
    //fprintf(stdout, "%s\t%d\t%.1f\n", mystu.name, mystu.age, mystu.score);
    FILE *fp = fopen("fscanf_fprintf_04.txt", "w+");
    if (!fp) {
        printf("failure!\n");
        exit(1);
    }

    while (true)
    {
        printf("输入姓名-年龄-成绩: \n");
        //标准输入,写入文件 
        fscanf(stdin, "%s%d%lf", mystu.name, &mystu.age, &mystu.score);
        //写入文件
        fprintf(fp, "%s\t%d\t%.2f\n", mystu.name, mystu.age, mystu.score);

        fflush(stdin);

        printf("是否继续?(Y/N)");
        int ch = getchar();
        if (ch == 'N' || ch == 'n') {
            break;
        }
    }

    fclose(fp);

    //读文件
    FILE *read = fopen("fscanf_fprintf_04.txt", "r+");
    if (!read) {
        printf("failure\n");
        exit(1);
    }

    while (fscanf(read, "%s%d%lf", mystu.name, &mystu.age, &mystu.score) > 0)
    {
        //标准输出
        fprintf(stdout, "%s\t%d\t%.2f\n", mystu.name, mystu.age, mystu.score);

    }

    fclose(read);

}

3.1 文件指针: fseek() + rewind() 

  •  ftell(fp): 现在所在位置(可用来求数据个数)

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>
#include <cstdlib>
#include <cstdio>
using namespace std;

/*
fseek: fseek(文件类型指针, 位移量, 起始点) 位移量必须是long类型
起始点: (宏)
SEEK_SET 文件首 0;
SEEK_CUR 文件当前位置 1;
SEEK_END 文件尾部 2;

以二进制形式存储数据
int fwrite(void *buffer,unsigned size, unsigned count, FILE * fp)
//以什么方式写进去就以什么方式读出 !!
int fread(void *buffer,unsigned size, unsigned count, FILE * fp)
*/
struct Student
{
    char name[20];
    int age;
    double num;
}stus[20];

int main()
{
    //以二进制形式写文件
    FILE *fp = fopen("fseek_rewind_06.txt", "wb+");
    if (!fp) {
        printf("failure!\n");
        exit(1);
    }
    int N;
    cin >> N; 
    for (int i = 0; i < N; i++)
    {
        printf("输入姓名-年龄-分数:\n");
        scanf("%s%d%lf", stus[i].name, &stus[i].age, &stus[i].num);
        fflush(stdin);
    }

    //写入文件
    //存N个数据
    fwrite(stus, sizeof(struct Student), N, fp);


    //fseek(文件类型指针, 位移量, 起始点) 位移量必须是long类型
    //SEEK_SET 文件首 0;
    //注意点: 移动多个位置, long L :表示
    //正负: 往后- 往前+
    fseek(fp, 0, SEEK_SET);

    //移动到第二个数据位置
    Student tmp;
    fseek(fp, 1L * sizeof(struct Student), SEEK_SET);
    fread(&tmp, sizeof(struct Student), 1, fp);
    printf("第二个数据: \n");
    printf("%s\t%d\t%.2f\n", tmp.name, tmp.age, tmp.num);

    //移动到最后一个位置(之后无元素)
    fseek(fp, 0, SEEK_END);
    long size = ftell(fp);       //ftell:现在所在位置(表达这个文件的大小)
    int number = size / sizeof(Student);
    printf("有几个数据%d: \n", number);
    
    //移动到最后一个元素之前位置 位移量必须是long类型,需要类型转换
    fseek(fp, -1L * (long)sizeof(struct Student), SEEK_END);
    fread(&tmp, sizeof(struct Student), 1, fp);
    printf("最后一个元素: \n");
    printf("%s\t%d\t%.2f\n", tmp.name, tmp.age, tmp.num);


    //直接移动到文件开始位置
    Student stu[20];
    rewind(fp); 
    printf("全部数据: \n");
    int len = fread(stu, sizeof(struct Student), N, fp);
    for (int i = 0; i < len; i++){
        printf("%s\t%d\t%.2f\n", stu[i].name, stu[i].age, stu[i].num);    
    }


    fclose(fp);
    
    return 0;

}

 

 

posted @ 2019-01-25 21:50  douzujun  阅读(2630)  评论(0编辑  收藏  举报