DWORD MyGetFileSize(const char* FileName)
{
FILE *fp = fopen(FileName, "rb");
if (NULL == fp)
{
return 0;
}
DWORD pos = ftell(fp);// 返回当前值,pos保存当前值
fseek(fp, 0, SEEK_END);// 定位到最后
DWORD size = ftell(fp); // 返回当前值,为文件大小size
fseek(fp, pos, SEEK_SET);// 设回原来的当前值
fclose(fp);
return size;
}
取得文件大小
下面贴个网上当来的FILE读写小例子:
//********************************************
// Ini 相关函数
//********************************************
#define VC_EXTRALEAN // Exclude rarely-used stuff from Windows headers
#include <afxwin.h> // MFC core and standard components
#include <afxext.h> // MFC extensions
#include <afxdisp.h> // MFC Automation classes
#include <afxdtctl.h> // MFC support for Internet Explorer 4 Common Controls
#include <afxcmn.h>
#ifndef _INI_H_
#define _INI_H_
#ifndef SAFE_DELETE
#define SAFE_DELETE(x) if( (x)!=NULL ) { delete (x); (x)=NULL; }
#endif
#ifndef SAFE_DELETE_ARRAY
#define SAFE_DELETE_ARRAY(x) if( (x)!=NULL ) { delete[] (x); (x)=NULL; }
#endif
#ifndef SAFE_FREE
#define SAFE_FREE(x) if( (x)!=NULL ) { free(x); (x)=NULL; }
#endif
#ifndef SAFE_RELEASE
#define SAFE_RELEASE(x) if( (x)!=NULL ) { (x)->Release(); (x)=NULL; }
#endif
#define ERROR_DATA -99999999
//配置文件类
class CIni
{
public:
bool Open(char *); // 打开配置文件
void Close(); // 关闭配置文件
void Save(char *filename=NULL); // 保存配置文件
int ReadInt(char *, char *); // 读一个整数
char *ReadText(char *, char *); // 读一个字符串
void Write(char *, char *, int); // 写一个整数
void Write(char *, char *, char *); // 写一个字符串
void DeleteIndex(char *index); // 删除一段
void DeleteName(char *index,char *name); // 删除段中一键名行
void AddIndex(char *); //加入一个索引
int FindHead(int index, char *string);
int FindIndex(char *); // 返回标题位置
CIni();
CIni(char*); //初始化打开配置文件
virtual ~CIni(); //释放内存
private:
void InitIndex(); // 初始化索引
int FindData(int, char *); // 返回数据位置
int GotoNextLine(int); // 获得下一行
char *ReadDataName(int &); // 在指定位置读一数据名称
char *ReadText(int); // 在指定位置读字符串
char *ReadHeadName(int &p);
void AddData(int, char *, char *); //在当前位置加入一个数据
void ModityData(int, char *, char *); //在当前位置修改一个数据的值
int GotoLastLine(char *index); //把指针移动到本INDEX的最后一行
char m_strFileName[MAX_PATH]; //文件名
long m_lDataLen; //文件长度
char *m_strData; //文件内容
int IndexNum; //索引数目([]的数目)
int *IndexList; //索引点位置列表
int Point; //当前指针
int Line, Word; //当前行列
};
#endif
.cpp
// Ini 相关函数
//------------------------------------------------------------------
// 包含
#include <stdio.h>
#include <stdlib.h>
#include <malloc.h>
#include <io.h>
#include <fcntl.h>
#include <assert.h>
#include "ini.h"
//-------------------------------------------------------------------
// 对外接口
//-------------------------------------------------------------------
//-------------------------------------------------------------------------------------
// 初始化/析构释放
//-------------------------------------------------------------------------------------
CIni::CIni()
{
m_lDataLen = 0;
m_strData = NULL;
IndexNum = 0;
IndexList = NULL;
}
CIni::CIni(char *filename)
{
m_lDataLen = 0;
m_strData = NULL;
IndexNum = 0;
IndexList = NULL;
Open(filename);
}
CIni::~CIni()
{
if( m_lDataLen != 0 )
{
SAFE_DELETE( m_strData );
m_lDataLen = 0;
}
if( IndexNum != 0 )
{
SAFE_DELETE( IndexList );
IndexNum = 0;
}
}
//-------------------------------------------------------------------------------------
// 功能:读入配置
// 入口:文件全路径;出口:无
//-------------------------------------------------------------------------------------
bool CIni::Open(char *filename)
{
strcpy(m_strFileName, filename);
SAFE_FREE( m_strData );
int fh;
fh = _open( filename, _O_RDONLY ); // 只读方式
if( fh== -1 )
m_lDataLen = -1;
m_lDataLen = _filelength(fh); // 获取文件长度
_close(fh);
if( m_lDataLen > 0 )// 文件存在
{
m_strData = new char[m_lDataLen];// 申请空间
FILE *fp;
fp=fopen(filename, "rb");
fread(m_strData, m_lDataLen, 1, fp);// 读数据
fclose(fp);
InitIndex(); // 初始化索引
return true;
}
else // 文件不存在
{
m_lDataLen=1;
m_strData = new char[m_lDataLen];
memset(m_strData, 0, 1);
InitIndex();
}
return false;
}
//-------------------------------------------------------------------------------------
// 功能:释放内存
// 入口:无;出口:无
//-------------------------------------------------------------------------------------
void CIni::Close()
{
if( m_lDataLen != 0 )
{
SAFE_DELETE( m_strData );
m_lDataLen = 0;
}
if( IndexNum != 0 )
{
SAFE_DELETE( IndexList );
IndexNum = 0;
}
}
//-------------------------------------------------------------------------------------
// 功能:写入文件
// 入口:文件全路径;出口:无
//-------------------------------------------------------------------------------------
void CIni::Save(char *filename)
{
if( filename==NULL )
filename=m_strFileName;
FILE *fp;
fp=fopen(filename, "wb");
fwrite(m_strData, m_lDataLen, 1, fp);
fclose(fp);
}
//-------------------------------------------------------------------------------------
// 功能:读一字符串数据
// 入口:段名,键名;出口:字符数据
//-------------------------------------------------------------------------------------
char *CIni::ReadText(char *index, char *name)
{
int n=FindIndex(index); // 找索引
int m=FindData(n, name); // 找键名
return ReadText(m); // 获得键值
}
//-------------------------------------------------------------------------------------
// 功能:读一整数
// 入口:段名,键名;出口:整数
//-------------------------------------------------------------------------------------
int CIni::ReadInt(char *index, char *name)
{
int n=FindIndex(index); // 找索引
int m=FindData(n, name); // 找键名
char *str=ReadText(m); // 获得键值
int ret=atoi(str); // 字符转化为整数
free(str);
return ret;
}
//-------------------------------------------------------------------------------------
// 功能:写一字符串数据
// 入口:段名,键名,键值;出口:无
//-------------------------------------------------------------------------------------
void CIni::Write(char *index, char *name, char *string)
{
int n=FindIndex(index);
if( n == -1 ) // index不存在,新建一个索引
{
AddIndex(index); // 添加索引
n=FindIndex(index); // 找到索引位置
n=GotoLastLine(index); // 取得它的下一行
AddData(n, name, string); //在当前位置n加一个数据
return ;
}
int m=FindData(n, name);// index索引存在
if( m==-1 ) // 索引存在,键名不存在,新建数据
{
n=GotoLastLine(index);
AddData(n, name, string); // 在当前位置n加一个数据
return ;
}
// 键名存在
ModityData(n, name, string); // 修改一个数据
return;
}
//-------------------------------------------------------------------------------------
// 功能:写一整数
// 入口:段名,键名,键值;出口:无
//-------------------------------------------------------------------------------------
void CIni::Write(char *index, char *name, int num)
{
char string[32];
sprintf(string, "%d", num);
int n=FindIndex(index);
if( n == -1 ) // 新建索引
{
AddIndex(index); // 添加一个索引
n=FindIndex(index);
n=GotoLastLine(index); // 获得本段最后一行
AddData(n, name, string); // 在当前位置n加一个数据
return;
}
int m=FindData(n, name); // 存在索引,找到键名首位置
if( m==-1 ) // 键名不存在,新建数据
{
n=GotoLastLine(index);
AddData(n, name, string); //在当前位置n加一个数据
return;
}
// 存在数据
ModityData(n, name, string); //修改一个数据
return;
}
//-------------------------------------------------------------------------------------
// 功能:删除一段
// 入口:段名;出口:无
//-------------------------------------------------------------------------------------
void CIni::DeleteIndex(char *index)
{
// char *name;
int n = FindIndex(index); // 找索引
if( n == -1 )
return; // 没有此段返回
n = GotoNextLine(n); // 获得首键名地址
// name = ReadHeadName(n); // 获得=之前的数据
// Write(index, name, 0);
// n = GotoNextLine(n);
int next = GotoLastLine(index); // 获得本段最后一行
if( m_strData[next] == EOF )
{
m_lDataLen = n; // 更新长度
m_strData = (char *)realloc(m_strData, m_lDataLen); // 重新分配内存
InitIndex(); // 更新索引
return;
}
char *temp=new char[m_lDataLen-next];
memcpy(temp, &m_strData[next], m_lDataLen-next); // 把next至最后的这一段长度内容保存
memcpy(&m_strData[n], temp, m_lDataLen-next); // 把next至最后的这一段长度内容向前移
m_lDataLen -= next-n; // 更新长度
m_strData = (char *)realloc(m_strData, m_lDataLen);
// 重新分配内存
InitIndex(); // 更新索引
}
//-------------------------------------------------------------------------------------
// 功能:删除一行
// 入口:段名;出口:无
//-------------------------------------------------------------------------------------
void CIni::DeleteName(char *index,char *name)
{
int m;
int n = FindIndex(index); // 找索引
if( n == -1 )
return; // 没有此段返回
n = FindHead(n, name); // 找键名
if( n == -1 ) // 键名不存在返回
return;
m = GotoNextLine(n); // 获得下一行的起始位置
char *temp=new char[m_lDataLen-m];
memcpy(temp, &m_strData[m], m_lDataLen-m); // 把m至最后的这一段长度内容保存
memcpy(&m_strData[n], temp, m_lDataLen-m); // 把m至最后的这一段长度内容向前移
m_lDataLen -= m-n; // 更新长度
m_strData = (char *)realloc(m_strData, m_lDataLen); // 重新分配内存
InitIndex(); // 更新索引
}
//--------------------------------------------------------------------------
// 内部函数
//--------------------------------------------------------------------------
//-------------------------------------------------------------------------------------
// 功能:计算出所有的索引位置
// 入口:无;出口:无
//-------------------------------------------------------------------------------------
void CIni::InitIndex()
{
IndexNum=0;
for(int i=0; i<m_lDataLen; i++)
{
if( m_strData[i]=='[' && ( m_strData[i-1]=='\n' || i==0 ) )// 找到一个
IndexNum++;
}
SAFE_DELETE( IndexList );
if( IndexNum>0 )
IndexList=new int[IndexNum];// 申请内存
int n=0;
for(i=0; i<m_lDataLen; i++)
{
if( m_strData[i]=='[' && ( m_strData[i-1]=='\n' || i==0 ) )
{
IndexList[n]=i+1; // 记录位置
n++;
}
}
}
//-------------------------------------------------------------------------------------
// 功能:返回指定段名位置
// 入口:指定段名;出口:首位置
//-------------------------------------------------------------------------------------
int CIni::FindIndex(char *string)
{
for(int i=0; i<IndexNum; i++)
{
char *str=ReadText( IndexList[i] );
if( strcmp(string, str) == 0 )
{
SAFE_FREE( str );
return IndexList[i];
}
SAFE_FREE( str );
}
return -1;
}
//-------------------------------------------------------------------------------------
// 功能:返回指定数据的位置
// 入口:索引,指定键名;出口:键名首位置
//-------------------------------------------------------------------------------------
int CIni::FindHead(int index, char *string)
{
int p=index; // 指针
char *name;
while(1)
{
p = GotoNextLine(p); // 获得下一行起始位置
name = ReadHeadName(p); // 获得=之前的数据
if( strcmp(string, name)==0 )
{
SAFE_FREE( name );
return p;
}
SAFE_FREE( name );
if( p>=m_lDataLen || m_strData[p] == '[' ) return -1;
}
return -1;
}
//-------------------------------------------------------------------------------------
// 功能:返回指定数据的位置
// 入口:索引,指定键名;出口:键名=号的位置
//-------------------------------------------------------------------------------------
int CIni::FindData(int index, char *string)
{
int p=index; // 指针
char *name;
while(1)
{
p = GotoNextLine(p); // 获得下一行起始位置
if( p>=m_lDataLen || m_strData[p] == '[' ) return -1;
name = ReadDataName(p); // 获得=之前的数据
if( strcmp(string, name)==0 )
{
SAFE_FREE( name );
return p;
}
SAFE_FREE( name );
}
return -1;
}
//-------------------------------------------------------------------------------------
// 功能:获得下一行起始位置
// 入口:位置;出口:下一行首位置
//-------------------------------------------------------------------------------------
int CIni::GotoNextLine(int p)
{
for(int i=p; i<m_lDataLen; i++)
{
if( m_strData[i]=='\n' )
return i+1;
}
return i;
}
//-------------------------------------------------------------------------------------
// 功能:在指定位置读一数据名称
// 入口:行首位置;出口:=号后的字符串
//-------------------------------------------------------------------------------------
char *CIni::ReadDataName(int &p)
{
char chr;
char *Ret;
int m=0;
Ret=new char[MAX_PATH];
memset(Ret, 0, MAX_PATH);
for(int i=p; i<m_lDataLen; i++)
{
chr = m_strData[i];
if( chr == '\r' || chr == '=' || chr == ';' )// 结束
{
p=i+1;
return Ret;
}
Ret[m]=chr;
m++;
}
return Ret;
}
//-------------------------------------------------------------------------------------
// 功能:在指定位置读一数据名称
// 入口:行首位置;出口:=号后的字符串
//-------------------------------------------------------------------------------------
char *CIni::ReadHeadName(int &p)
{
char chr;
char *Ret;
int m=0;
Ret=new char[MAX_PATH];
memset(Ret, 0, MAX_PATH);
for(int i=p; i<m_lDataLen; i++)
{
chr = m_strData[i];
if( chr == '\r' || chr == '=' || chr == ';' )// 结束
{
return Ret;
}
Ret[m]=chr;
m++;
}
return Ret;
}
//-------------------------------------------------------------------------------------
// 功能:在指定位置读一字符串,p为索引位置
// 入口:行首位置;出口:=号前的字符串
//-------------------------------------------------------------------------------------
char *CIni::ReadText(int p)
{
char chr;
char *Ret;
int n=p, m=0;
int LineNum = GotoNextLine(p) - p + 1;
Ret=new char[LineNum];
memset(Ret, 0, LineNum);
for(int i=0; i<m_lDataLen-p; i++)
{
chr = m_strData[n];
if( chr == ';' || chr == '\r' || chr == '\t' || chr == ']' )// 结束
{
return Ret;
}
Ret[m]=chr;
m++;
n++;
}
return Ret;
}
//-------------------------------------------------------------------------------------
// 功能:加入一个索引
// 入口:索引;出口:无
//-------------------------------------------------------------------------------------
void CIni::AddIndex(char *index)
{
char str[MAX_PATH];
memset(str, 0, MAX_PATH);
sprintf(str,"\r\n[%s]\r\n",index);
m_strData = (char *)realloc(m_strData, m_lDataLen+strlen(str)); // 重新分配内存
sprintf(&m_strData[m_lDataLen], "%s", str); // 写入索引
m_lDataLen+=strlen(str); // 长度指向最后
InitIndex(); // 重建索引
}
//-------------------------------------------------------------------------------------
// 功能:在当前位置加入一个数据
// 入口:当前行的首点,键名,键值;出口:无
//-------------------------------------------------------------------------------------
void CIni::AddData(int p, char *name, char *string)
{
char *str;
int len;
str=new char[2*MAX_PATH];
memset(str, 0, 2*MAX_PATH);
sprintf(str,"%s=%s\r\n",name,string);
len=strlen(str);
m_strData = (char *)realloc(m_strData, m_lDataLen+len); // 重新分配内存
char *temp=new char[m_lDataLen-p];
memcpy(temp, &m_strData[p], m_lDataLen-p); // 把p至最后的这一段长度内容保存
memcpy(&m_strData[p+len], temp, m_lDataLen-p); // 把p至最后的这一段长度内容向后移
memcpy(&m_strData[p], str, len); // 在p存入字符串
m_lDataLen+=len; // 长度增加
SAFE_DELETE(temp);
SAFE_DELETE(str);
InitIndex(); // 更新索引
}
//-------------------------------------------------------------------------------------
// 功能:在当前位置修改一个数据的值
// 入口:当前行的首点,键名,键值;出口:无
//-------------------------------------------------------------------------------------
void CIni::ModityData(int p, char *name, char *string)
{
int n=FindData(p, name);
char *t=ReadText(n);
p=n+strlen(t); // p指向本行最后,n指向=号后
if( strlen(t)>0 ) free(t);
int newlen=strlen(string);
int oldlen=p-n;
m_strData = (char *)realloc(m_strData, m_lDataLen+newlen-oldlen); // 重新分配内存
char *temp=new char[m_lDataLen-p];
memcpy(temp, &m_strData[p], m_lDataLen-p); // 把p至最后的这一段长度内容保存
memcpy(&m_strData[n+newlen], temp, m_lDataLen-p); // 把p至最后的这一段长度内容向后移
memcpy(&m_strData[n], string, newlen); // 在n存入新字符串
m_lDataLen+=newlen-oldlen; // 更新长度
SAFE_DELETE( temp );
InitIndex(); // 更新索引
}
//-------------------------------------------------------------------------------------
// 功能:把指针移动到本INDEX的最后一行
// 入口:索引点;出口:段内最后一行首位置
//-------------------------------------------------------------------------------------
int CIni::GotoLastLine(char *index)
{
int n=FindIndex(index);
n=GotoNextLine(n);
while(1)
{
if( m_strData[n] == '\r' || m_strData[n] == EOF || m_strData[n] == -3 || m_strData[n] == ' ' || m_strData[n] == '/' || m_strData[n] == '\t' || m_strData[n] == '\n' )
{
return n;
}
else
{
n=GotoNextLine(n);
if( n >= m_lDataLen ) return n;
}
}
}