C++ fstream详解[通俗易懂]

C++ fstream详解[通俗易懂]C语言里面对文件的操作是通过文件指针,以及一些相关的函数,那么C++中是如何对文件进行操作的呢?没错,就是通过fstream这个文件流来实现的。当我们使用#include时,我们就可以使用其中的ifstream,ofstream以及fstream这三个类了(ofstream是从内存到硬盘,ifstream是从硬盘到内存),也就可以用这三个类来定义相应的对象了,这三个类分别代表一个输入文件…

大家好,又见面了,我是你们的朋友全栈君。如果您正在找激活码,请点击查看最新教程,关注关注公众号 “全栈程序员社区” 获取激活教程,可能之前旧版本教程已经失效.最新Idea2022.1教程亲测有效,一键激活。

Jetbrains全系列IDE使用 1年只要46元 售后保障 童叟无欺

C语言里面对文件的操作是通过文件指针,以及一些相关的函数,那么C++中是如何对文件进行操作的呢?没错,就是通过 fstream 这个文件流来实现的。当我们使用#include 时,我们就可以使用其中的 ifstream,ofstream以及fstream 这三个类了(ofstream是从内存到硬盘,ifstream是从硬盘到内存),也就可以用这三个类来定义相应的对象了,这三个类分别代表一个输入文件,一个输出文件,以及一个输入输出文件。Ifstream类支持>>操作符,ofstream类支持<<操作符,fstream类同时支持>>和<<操作符。

C语言文件操作

函数 fopen()将一个文件和一个流关联起来,并初始化一个类型为 FILE 的对象,该对象包含了控制该流的所有信息。这些信息包括指向缓冲区的指针;文件位置指示器,它指定了获取文件的位置;以及指示错误和文件结尾情况的标志。
每个用于打开文件的函数(也就是 fopen()、freopen()和 tmpfile())都会返回一个指向 FILE 对象的指针,该 FILE 对象包含与被打开文件相关联的流。一旦打开了文件,就可以调用函数传递数据并对流进行处理。这些函数都把指向 FILE 对象的指针(通常称为 FILE 指针)作为它们的参数之一。FILE 指针指定了正在进行操作的流

FILE *fopen( const char * restrict filename,const char * restrict mode );
FILE *freopen(const char * restrict filename,
                  const char * restrict mode,
                  FILE * restrict stream );
FILE *tmpfile( void );

所有三个打开文件的函数 fopen()、freopen()和 tmpfile(),都会返回一个指针。如果成功,该指针就指向已打开的流,如果失败,该指针就为空指针

#include <stdio.h>
#include <stdbool.h>
_Bool isReadWriteable( const char *filename )
{ 
   
  FILE *fp = fopen( filename, "r+" );   // 打开一个文件以用于读写
  if ( fp != NULL )                             // fopen()是否执行成功
  { 
   
    fclose(fp);                                 // 成功:关闭文件,没有错误需要处理
    return true;
  }
  else                                          // 失败
    return false;
}

关闭文件时需要使用函数 fclose()

int fclose( FILE *fp );

正常返回:0。
异常返回:EOF,表示文件在关闭时发生错误。

C++文件操作

1.直接使用流对象进行文件的操作,默认方式如下:

ofstream out("...", ios::out);
ifstream in("...", ios::in);
fstream foi("...", ios::in|ios::out);

文件写操作

 // writing on a text file
#include <fiostream.h>
int main () { 
   
    ofstream out("out.txt");
    if (out.is_open()) 
   { 
   
        out << "This is a line.\n";
        out << "This is another line.\n";
        out.close();
    }
    return 0;
}

文件读操作

 // reading a text file
#include <iostream.h>
#include <fstream.h>
#include <stdlib.h>
int main () { 
   
    char buffer[256];
    ifstream in("test.txt");
    if (! in.is_open())
    { 
    cout << "Error opening file"; exit (1); }
    while (!in.eof() )
    { 
   
        in.getline (buffer,100);
        cout << buffer << endl;
    }
    return 0;
}

2.open函数

void open ( const char * filename,  
            ios_base::openmode mode = ios_base::in | ios_base::out );  

void open(const wchar_t *_Filename,  
        ios_base::openmode mode= ios_base::in | ios_base::out,  
        int prot = ios_base::_Openprot)

参数:

filename 操作文件名

mode 打开文件的方式

prot 打开文件的属性 //基本很少用到,在查看资料时,发现有两种方式

**打开文件的方式(mode ): **

ios::app:    //以追加的方式打开文件  
ios::ate:    //文件打开后定位到文件尾,ios:app就包含有此属性  
ios::binary:  //以二进制方式打开文件,缺省的方式是文本方式。两种方式的区别见前文  
ios::in:     //文件以输入方式打开(文件数据输入到内存)  
ios::out:    //文件以输出方式打开(内存数据输出到文件)  
ios::nocreate: //不建立文件,所以文件不存在时打开失败  
ios::noreplace://不覆盖文件,所以打开文件时如果文件存在失败  
ios::trunc:   //如果文件存在,把文件长度设为0

打开文件的属性取值(prot ):

0:普通文件,打开访问  
1:只读文件  
2:隐含文件  
4:系统文件 
可以用“或”或者“+”把以上属性连接起来,如3或1|2就是以只读和隐含属性打开文件

状态标志符:

除了eof()以外,还有一些验证流的状态的成员函数(所有都返回bool型返回值):

is_open():文件是否正常打开
bad():读写过程中是否出错(操作对象没有打开,写入的设备没有空间)
fail():读写过程中是否出错(操作对象没有打开,写入的设备没有空间,格式错误--比如读入类型不匹配)
eof():读文件到达文件末尾,返回true
good():以上任何一个返回true,这个就返回false

要想重置以上成员函数所检查的状态标志,你可以使用成员函数clear(),没有参数

获得和设置流指针

- 对于所有的输入输出流都有至少一个指针,指向下一个要操作的位置

ofstream  put_point

ifstream  get_point

fstream  put_point和get_point

- 获取流指针位置

tellg(): 返回输入流指针的位置(返回类型long)

tellp(): 返回输出流指针的位置(返回类型long)

- 设置指针位置

seekg(long  position):  设置输入流指针位置为第position个字符(文件首位置为开始位置)

seekp(long  position):  设置输出流指针到指定位置
// position in output stream
#include <fstream> // std::ofstream

int main () { 
   

  std::ofstream outfile;
  outfile.open ("test.txt");

  outfile.write ("This is an apple",16);
  long pos = outfile.tellp();
  outfile.seekp (pos-7);
  outfile.write (" sam",4);

  outfile.close();

  return 0;
}

seekg ( off_type offset, seekdir direction );
seekp ( off_type offset, seekdir direction );
使用这个原型可以指定由参数direction决定的一个具体的指针开始计算的一个位移(offset)。它可以是:

ios::beg 从流开始位置计算的位移
ios::cur 从流指针当前位置开始计算的位移
ios::end 从流末尾处开始计算的位移

//假设test.txt中的内容是HelloWorld
ifstream fin("test.txt",ios::in);
cout << fin.tellg();//输出0,流置针指向文本中的第一个字符,类似于数组的下标0

char c;
fin >> c;
fin.tellg();//输出为1,因为上面把fin的第一个字符赋值给了c,同时指针就会向后 移动一个字节(注意是以一个字节为单位移动)指向第二个字符

fin.seekg(0,ios::end);//输出10,注意最后一个字符d的下标是9,而ios::end指向的是最后一个字符的下一个位置

fin.seekg(10,ios::beg);//和上面一样,也到达了尾后的位置

//我们发现利用这个可以算出文件的大小

int m,n;
m = fin.seekg(0,ios::beg);
n =  fin.seekg(0,ios::end);
//那么n-m就是文件的所占的字节数

我们也可以从文件末尾出发,反向移动流指针,
fin.seekg(-10,ios::end);//回到了第一个字符

读取文件内容:

// print the content of a text file.
#include <iostream> // std::cout
#include <fstream> // std::ifstream

int main () { 
   
  std::ifstream ifs;

  ifs.open ("test.txt", std::ifstream::in);

  char c = ifs.get();

  while (ifs.good()) { 
   
    std::cout << c;
    c = ifs.get();
  }

  ifs.close();

  return 0;
}

使用重载的’<<’ 或者 ‘>>’, 也可以使用成员函数来实现

#include <fstream>
using namespace std;

int main ()
{ 
   
    ifstream fr;
    ofstream fw;
    char word[200], line[200];
    
    fw.open("write.txt");
    fr.open("read.txt");
    
    fr  >> word;    //读取文件,一个单词
    fr.getline (line, 100);        //读取一行内容
    
    fw << "write file test" << endl;
    
    fw.close();
    fr.close();
    
    return 0;
}

参考:
http://www.cplusplus.com/reference/fstream/ifstream/open/

https://www.cnblogs.com/journal-of-xjx/p/6679663.html

https://www.cnblogs.com/alihenaixiao/p/6429854.html

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-用户IM,转载请注明出处:https://javaforall.cn/191645.html原文链接:https://javaforall.cn

【正版授权,激活自己账号】: Jetbrains全家桶Ide使用,1年售后保障,每天仅需1毛

【官方授权 正版激活】: 官方授权 正版激活 支持Jetbrains家族下所有IDE 使用个人JB账号...

(0)


相关推荐

  • 如何将InputStream转换为String

    2019独角兽企业重金招聘Python工程师标准>>>…

  • vbs代码弹计算机,如何恶搞朋友的电脑?超简单的vbs代码

    vbs代码弹计算机,如何恶搞朋友的电脑?超简单的vbs代码这东西不好做成视频教程,我们就做成文章出来分享吧!编写vbs有多简单?新建“文本文档”,输入msgbox”一大波病毒正在靠近…”,点击文件->另存为->重命名为“代码.vbs”。文件名不重要,重要的是后缀要是“.vbs”双击保存的文件:代码.vbs,即弹出一个对话框。记下这段小小的代码,去同学家里恶搞吧。当然你还可以输入其他有趣的文字。当然,如此恶搞还是不够的。那就来一个无限循…

  • 深信服SCSA安全认证工程师

    深信服SCSA安全认证工程师深信服SCSA安全认证工程师考试实验环境在线学习课程讲师在线学习视频(SCSI)学员在线学习视频(SCSA)在线题库考试考试入口试卷自动批阅错题集记录联系方式微信联系18849911

  • 虚拟机与宿主机网络[通俗易懂]

    虚拟机与宿主机网络[通俗易懂]桥接、NAT和host-only三种网络连接方式的区别一、不同网络连接方式对网络网络影响简介:二、三种网络连接方式详细介绍:我本机宿主机使用win10系统,IP地址为:192.168.1.117。1、桥接方式桥接方式下,虚拟机和宿主机处于同一网段,真实存在于网络中,像是一台真实的主机。虚拟机和宿主机彼此互通,且网络中的其他主机也可以互通。就像是连接在hub中的主机一样。获取的IP地址网段为:192.168.1.X,实际获取的为192.168.1.220。优点:可以轻松实现上网,同网段中的主机

  • NPOI导出Excel并下载到客户端

    NPOI导出Excel并下载到客户端利用NPOI导出Excel,把Excel发送到客户端

  • c++的发展方向

    c++的发展方向我现在是一名在校大学生,在学校期间自学C++有两年的时间了,看过C++Primer,stl,insideC++model(侯捷翻译的那本),com本质论等… 在学习C++的过程中感觉C++语言本身的确很强大,而且随着学习的深入,我逐渐感到要想在短时间了解这门语言的本质几乎是不可能的.因为我也学习过javaSE的一些东西,感觉就java和C#来说,语言本身不难,不过在底层调用方面有时候就

发表回复

您的电子邮箱地址不会被公开。

关注全栈程序员社区公众号