配置文件读写

需求:将文件的有效内容截取出来,并且放入到一个键值对的数组中

  • struct ConfigInfo{char key[64];char value[64]};
  • 获取有效行数
  • 判断当前行是否有效
  • 解析数据 parseFile
    • 将有效数据放入到数组中,数组在堆区开辟
  • 根据key获取value getInfoByKey
  • 释放内存 freeSpace

代码示例:

文件读写配置.c

#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
struct Person
{
   
        char a;
        int b;
};
void test01()
{
   
        char *filePath = "./config.txt";
        int line = getFileLine(filePath);
        printf("文件的有效行数为:%d\n",line);
        struct ConfigInfo*pArray = NULL;
        parseFile(filePath,line,&pArray);
        //测试 根据key访问value
        printf("heroId=%s\n", getInfoByKey("heroId", pArray, line));
        printf("heroName=%s\n", getInfoByKey("heroName", pArray, line));
        printf("heroAtk=%s\n", getInfoByKey("heroAtk", pArray, line));
        printf("heroDef=%s\n", getInfoByKey("heroDef", pArray, line));
        printf("***fo=%s\n", getInfoByKey("***fo", pArray, line));
        //释放内存
        freeSpace(pArray);
        pArray = NULL;
}
int main()
{
   
        test01();
        return EXIT_SUCCESS;
}

config.c

#include"config.h"
//获取有效行数
int getFileLine(char*fileName)
{
   
        FILE*file = fopen(fileName,"r");
        if (file == NULL)
        {
   
               return -1;
        }
        char buf[1024] = {
   0};
        int lines = 0;
        while (fgets(buf,1024,file)!=NULL)
        {
   
               //如果是有效行 才统计
               if (isValidLine(buf))
               {
   
                       lines++;
               }
               
        }
        fclose(file);
        return lines;
}
//判断当前行是否有效
int isValidLine(char*str)
{
   
        if (str[0] == ' ' || str[0] == '\0' || strchr(str, ':') == NULL)
        {
   
               return 0;//有效数据都返回假
        }
        return 1;
}
//解析文件
void parseFile(char*filePath, int lines, struct ConfigInfo** configInfo)
{
   
        struct ConfigInfo*info= malloc(sizeof(struct ConfigInfo)*lines);
        if (info == NULL)
        {
   
               return;
        }
        FILE*file = fopen(filePath,"r");
        char buf[1024] = {
    0 };
        int index = 0;
        while (fgets(buf,1024,file)!=NULL)
        {
   
               //解析数据 有效数据才解析
               //heroName:aaaaa
               if (isValidLine(buf))
               {
   
                       memset(info[index].key,0,64);
                       memset(info[index].value, 0, 64);
               char*pos=strchr(buf, ':');//pos代表冒号所在位置
               strncpy(info[index].key, buf,pos - buf);     //将key截取到结构中
               strncpy(info[index].value,  pos+1,strlen(pos+1)-1);
               //printf("key= %s\n",info[index].key);
               //printf("value= %s", info[index].value);
               index++;
               }
               memset(buf,0,1024);
        }
        *configInfo = info;
}
//根据索引值 获取 实值
char*getInfoByKey(char*key, struct ConfigInfo*configInfo, int line)
{
   
        for (int i = 0; i < line; i++)
        {
   
               if (strcmp(key, configInfo[i].key) == 0)
               {
   
                       return configInfo[i].value;
               }
        }
        return NULL;
}
//释放信息
void freeSpace(struct ConfigInfo*configInfo)
{
   
        if (configInfo != NULL)
        {
   
               free(configInfo);
               configInfo = NULL;
        }
}

config.h

#pragma once
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
struct ConfigInfo
{
   
        char key[64];//索引值
        char value[64];//实值
};
//获取有效行数
int getFileLine(char*fileName);
//判断当前行是否有效
int isValidLine(char*str);
//解析文件
void parseFile(char*filePath,int lines,struct ConfigInfo** configInfo);
//根据索引值 获取 实值
char*getInfoByKey(char*key,struct ConfigInfo*configInfo,int line);
//释放信息
void freeSpace(struct ConfigInfo*configInfo);