VS2010/MFC编程入门之四十五(MFC常用类:CFile文件操作类)
上一节中鸡啄米讲了定时器Timer的用法,本节介绍下文件操作类CFile类的使用。
CFile类概述
如果你学过C语言,应该知道文件操作使用的是文件指针,通过文件指针实现对它指向的文件的各种操作。这些文件操作函数中有的最终还是调用了操作系统的API函数或者处理过程与之类似,例如在Windows系统中,fread函数就调用了API函数ReadFile。
Windows系统的API函数除了ReadFile,还有CreateFile、WriteFile等函数。而MFC基于面向对象的思想,将这些Windows API函数封装到了CFile类中,实现对文件的打开、关闭、读、写、获取文件信息等操作。使用CFile类对文件进行操作非常便捷。
CFile类的成员函数
CFile( );
CFile(HANDLE hFile);
CFile(LPCTSTR lpszFileName,UINT nOpenFlags);
以上三个成员函数都是CFile的构造函数,用于构造CFile对象。参数hFile为要关联到CFile对象的文件的句柄。参数lpszFileName为要关联到CFile对象的文件的相对路径或者绝对路径;参数nOpenFlags为文件访问选项的组合,通过各选项的按位或运算实现组合,下面的5个表列出了nOpenFlags参数可能取的选项:
下面的文件访问模式选项表中只能选择一个进行组合,默认取CFile::modeRead。
| 取值 | 描述 |
| CFile::modeRead | 只读方式访问文件 |
| CFile::modeWrite | 写入方式访问文件 |
| CFile::modeReadWrite | 读写方式访问文件 |
下面的文件共享模式选项表中也只能选择一个进行组合,默认的共享模式是CFile::shareExclusive。
| 取值 | 描述 |
| CFile::shareDenyNone | 允许其他进程对文件进行读写 |
| CFile::shareDenyRead | 不允许其他进程读取文件 |
| CFile::shareDenyWrite | 不允许其他进程写文件 |
| CFile::shareExclusive | 禁止其他进程对文件的所有访问 |
下面的文件创建模式选项列表中可选择第一个或两者都选进行组合。
| 取值 | 描述 |
| CFile::modeCreate | 如果文件不存在则创建文件,而如果存在则将它关联到此CFile对象并将长度截取为0 |
| CFile::modeNoTruncate | 如果文件不存在则创建文件,而如果存在则将它关联到此CFile对象而不进行截取 |
注意,选择CFile::modeNoTruncate时需要与CFile::modeCreate一起使用,即CFile::modeCreate | CFile::modeNoTruncate。
另外,还有一个文件缓冲选项列表和一个文件安全选项。文件缓冲选项不太常用,鸡啄米这里就不讲了,有兴趣的可以查阅MSDN。文件安全选项是CFile::modeNoInherit,意为禁止子进程继承使用此文件。
当然,在实际使用时,以上各个表并不是都要用到,大家可以根据自己的需要选择用哪个表,选择哪个选项。
virtual BOOL Open(LPCTSTR lpszFileName,UINT nOpenFlags,CFileException* pError = NULL);
打开文件。它通常与默认构造函数CFile::CFile()一起使用。参数lpszFileName和nOpenFlags同构造函数。参数pError为指向文件异常对象的指针,默认为NULL。
virtual void Close( );
关闭文件。如果你没有在执行析构函数前调用此成员函数关闭文件,则析构函数会为你关闭。
virtual UINT Read(void* lpBuf,UINT nCount);
读取文件数据到缓存。参数lpBuf是由用户提供的指向接收文件数据的缓存的指针;参数nCount为读取的最大字节数。返回值是实际读取到缓存的字节数,如果到达文件尾则返回值可能会小于nCount,此时继续读取的话,会返回0,所以通常我们都会判断返回值是否小于nCount或者等于0来确定是否到达文件尾。
virtual void Write(const void* lpBuf,UINT nCount);
将缓存中的数据写入文件。参数lpBuf也是由用户提供,指向包含写入数据的缓存的指针;参数nCount为缓存中要被写入文件的数据的字节数。
virtual ULONGLONG Seek(LONGLONG lOff,UINT nFrom);
在一个打开的文件中重定位文件指针。参数lOff为文件指针移动的字节个数,为正数时表示向文件尾移动,为负数时表示向文件开头移动;参数nFrom为lOff的基准位置,即由nFrom位置开始移动lOff个字节,它可以取下面几个值中的一个:
CFile::begin 从文件开头开始移动
CFile::current 从文件指针的当前位置开始移动
CFile::end 从文件尾开始移动
文件打开时,文件指针被置于0,即文件开头处。
如果此函数成功则返回文件指针的位置。
void SeekToBegin( );
将文件指针移动到文件开头。它等价于Seek( 0L, CFile::begin )。
ULONGLONG SeekToEnd( );
将文件指针移动到文件末尾。返回值是文件的字节长度。它等价于CFile::Seek( 0L, CFile::end )。
virtual ULONGLONG GetLength( ) const;
获取文件的字节长度。
virtual void SetLength(ULONGLONG dwNewLen);
改变文件的长度。参数dwNewLen为文件的新长度,它可能比文件的当前长度值要大或者小,文件会相应的被扩展或截取。
virtual CString GetFileName( ) const;
获取文件名称。
virtual CString GetFilePath( ) const;
获取文件的绝对路径。
virtual CString GetFileTitle( ) const;
获取文件的显示名称。举个例子,与GetFileName区分一下,如果你系统中的文件不显示扩展名,则它获取到的文件名称就不包含扩展名,否则就显示扩展名。
virtual ULONGLONG GetPosition( ) const;
获取文件指针的当前位置。
static void PASCAL Remove(LPCTSTR lpszFileName,CAtlTransactionManager* pTM = NULL);
删除文件。参数lpszFileName为要删除的文件路径,可以是相对路径、绝对路径或者网络路径;参数pTM指向一个CAtlTransactionManager对象。
static void PASCAL Rename(LPCTSTR lpszOldName,LPCTSTR lpszNewName,CAtlTransactionManager* pTM = NULL);
重命名文件。参数lpszOldName为老的文件路径;参数lpszNewName为新的文件路径;参数pTM指向一个CAtlTransactionManager对象。实际上此函数的意义已经不只是重命名文件,还可以移动文件到其他目录下,例如,lpszOldName取"d:\\1.txt",lpszNewName取"e:\\2.txt",这样可以将D盘中的1.txt文件转移到E盘并重命名为2.txt。
CFile类应用实例
这里鸡啄米只给大家演示几个简单的代码片段,从这些代码片段中熟悉CFile类的文件操作。
实例一:构造CFile对象时就打开文件,然后向文件中写入数据,最后以Seek函数移动文件指针,读取文件内容。
- char writeBuffer[500]; // 要写入的数据的缓存
- char readBuffer[500]; // 存放读取数据的缓存
- LONGLONG lOff = 0; // 文件指针的偏移量,也是读取到的数据的总字节数
- // 构造CFile对象,同时以创建和读写的方式打开文件E:\1.txt
- CFile file(_T("e:\\1.txt"), CFile::modeCreate | CFile::modeReadWrite);
- // 将写入数据的缓存中每个字节都赋值为字符c
- memset(writeBuffer, 'c', sizeof(writeBuffer));
- // 将数据写入到文件中
- file.Write(writeBuffer, sizeof(writeBuffer));
- while (true)
- {
- // 以文件开头为基准,移动文件指针到lOff的位置
- file.Seek(lOff, CFile::begin);
- // 读取100个字节的数据到存放读取数据的缓存的readBuffer + lOff位置处
- int nRet = file.Read(readBuffer + lOff, 100);
- // 根据实际读取的字节数,增加文件指针的移动量
- lOff += nRet;
- // 如果读取数据时返回值小于指定的100,说明已到文件尾,跳出循环
- if (nRet < 100)
- break;
- }
- // 关闭文件
- file.Close();
实际上,在Write函数和Read函数执行后,文件指针会自动移动到最后操作的位置,所以其实上面的代码中无须使用Seek函数再去手动移动文件指针。这将在下面的实例二中体现出来。
实例二:构造CFile对象,然后使用Open成员函数打开文件,再写入一个结构体数组,最后读取出来。
先贴上结构体的定义:
- struct student
- {
- int nNum;
- float fScore;
- };
下面是文件操作的代码片段:
- student s1[2]; // 存放要写入文件的数据
- student s2[2]; // 存放从文件读取的数据
- CFile file; // CFile对象
- int nReadBytes = 0; // 从文件中读取到的总字节数
- // 为s1数组各元素赋值
- s1[0].nNum = 22;
- s1[0].fScore = 91.5;
- s1[1].nNum = 23;
- s1[1].fScore = 85;
- // 以创建、读写方式打开文件E:\1.txt
- if (file.Open(_T("E:\\1.txt"), CFile::modeCreate | CFile::modeReadWrite))
- {
- // 写入数据s1结构体数组
- file.Write(s1, sizeof(s1));
- // 因为上面调用Write以后文件指针在文件尾,所以需要将其移动到文件开头
- file.SeekToBegin();
- while (true)
- {
- // 读取数据到s2
- int nRet = file.Read((BYTE*)s2 + nReadBytes, sizeof(student));
- // 计算已经读取到的总字节数
- nReadBytes += nRet;
- // 如果读取数据时返回值小于指定的sizeof(student),则说明已到文件尾,跳出循环
- if (nRet < sizeof(student))
- break;
- }
- // 关闭文件
- file.Close();
- }
本节内容就到这里,如果有其他语言的文件操作的经验的话,应该还是比较简单的。鸡啄米很高兴能在大家的编程入门之路上贡献自己一点微薄的力量。
转自:http://www.jizhuomi.com/software/181.html
VS2010/MFC编程入门之四十五(MFC常用类:CFile文件操作类)的更多相关文章
- VS2010/MFC编程入门之三十五(菜单:菜单及CMenu类的使用)
鸡啄米在上一节中讲的是VS2010的菜单资源,本节主要讲菜单及CMenu类的使用. CMenu类的主要成员函数 MFC为菜单的操作提供了CMenu类,下面鸡啄米就常用的几个成员函数进行简单的介绍. B ...
- VS2010/MFC编程入门之四十六(MFC常用类:MFC异常处理)
上一节中鸡啄米讲了CFile文件操作类,本节主要来说说MFC异常处理. 在鸡啄米C++编程入门系列的最后一节鸡啄米:C++编程入门系列之五十(异常处理)中,鸡啄米讲了C++标准异常的处理机制,如果你还 ...
- VS2010/MFC编程入门之四十四(MFC常用类:定时器Timer)
前面一节鸡啄米讲了CTime类和CTimeSpan类的使用,本节继续讲与时间有关的定时器.定时器并不是一个类,主要考虑到,提起时间的话就不能不说定时器,所以就把它放到CTime和CTimeSpan之后 ...
- VS2010/MFC编程入门之四十四:定时器Timer
前面一节鸡啄米讲了CTime类和CTimeSpan类的使用,本节继续讲与时间有关的定时器.定时器并不是一个类,主要考虑到,提起时间的话就不能不说定时器,所以就把它放到CTime和CTimeSpan之后 ...
- VS2010/MFC编程入门之四十二(MFC常用类:CString类)
上一节鸡啄米讲了分割窗口的有关知识,本节开始讲解MFC的一些常用类,先来说说CString类. CString类简介 CString类作为MFC的常用类,当之无愧.可以这样说,只要是从事MFC开发,基 ...
- VS2010/MFC编程入门之四十三(MFC常用类:CTime类和CTimeSpan类)
上一节中鸡啄米讲了MFC常用类CString类的用法,本节继续讲另外两个MFC常用类-日期和时间类CTime类和CTimeSpan类. 日期和时间类简介 CTime类的对象表示的时间是基于格林威治标准 ...
- VS2010/MFC编程入门之四十九(图形图像:CDC类及其屏幕绘图函数)
上一节中鸡啄米讲了文本输出的知识,本节的主要内容是CDC类及其屏幕绘图函数. CDC类简介 CDC类是一个设备上下文类. CDC类提供了用来处理显示器或打印机等设备上下文的成员函数,还有处理与窗口客户 ...
- VS2010/MFC编程入门之四十八(字体和文本输出:文本输出)
鸡啄米在上一节中讲了CFont字体类,本节主要讲解文本输出的方法和实例. 文本输出过程 在文本输出到设备以前,我们需要确定字体.字体颜色和输出的文本内容等信息.Windows窗口的客户区由应用程序管理 ...
- VS2010/MFC编程入门之四十(文档、视图和框架:各对象之间的关系)
前面一节中鸡啄米进行了文档.视图和框架的概述,本节主要讲解文档.视图.框架结构中各对象之间的关系. 各个对象之间的关系 文档.视图.框架结构中涉及到的对象主要有:应用程序对象.文档模板对象.文档对象. ...
随机推荐
- Artech的MVC4框架学习——第四章Model元数据的解析
总结: 第一Model元数据是针对 数据类型的一种表述信息. 第二Model元数据作用:控制数据类型本身及其成员,通过相应的特性,在view中 为绑定的数据(Model)实现模版化的html呈现. 第 ...
- jQuery的ajax跨域 Jsonp原理
1.Jsonp Jsonp(json with padding)是JSON的一种“使用模式”,可用于解决主流浏览器的跨域数据访问的问题. Jsonp是为了解决ajax跨域发送http请求出现的,利用S ...
- jenkins之另辟蹊径实现根据svn项目实现智能选择
项目要求,根据svn选择的trunk或branches及tags里的各分支,动态选择参数.一开始认为很简单,直接用jenkins中的List Subversion tags插件及active choi ...
- linux文件归档脚本
#!/bin/bash range= dir="/app/xx/logs" bak_dir="/app/xx/logs_archive" cd $dir $ra ...
- Java开发之上帝之眼系列教程前言&目录
前言 如果您正在为Java后端庞大的体系所困扰,如果您正在为各种繁出不穷的技术和各种框架所迷茫,那么本系列文章将带您窥探Java庞大的体系.本系列教程希望您能站在上帝的角度去观察(了解)Java体系. ...
- java 中静态变量(类变量)与实例变量 静态方法与实例方法
静态变量: 在类内部中,方法的外部声明的对象而且加上static; 实例变量: 在类内部中,声明不需要加static; 比如: public class Demo{ int i1=0; static ...
- R数据可视化手册学习——条形图
1. 绘制简单条形图 # 使用ggplot2和gcookbook library(ggplot2); library(gcookbook) g <- ggplot(data = pg_mean, ...
- 11.23CSS笔记
每一步的编写过程都在代码里面书写了,暂且记录下来 <!DOCTYPE html> <html lang="en"> <head> <met ...
- Oracle体系结构之数据文件管理
数据文件分2个方向管理: 物理结构和逻辑结构. 数据库的存储层次结构图: ............. 逻辑结构: 物理结构: .... ...
- The third column indicates whether subclasses of the class declared outside this package have access to the member.;
总结1.modifier 改性剂 修饰符 修饰语 调节器access modifier 访问修饰符 存取权限 存取修饰词 存取修饰字官网“can”Access level modifiers dete ...