VC驿站

 找回密码
 加入驿站

QQ登录

只需一步,快速开始

搜索
查看: 436|回复: 6

[已解决]《实用C++》第45课文件指针小作业执行代码后,为什么会多出5个字节?

[复制链接]
63_avatar_middle
最佳答案
1 
donate_vip 发表于 2019-11-2 11:24:54 | 显示全部楼层 |阅读模式


4、小作业:
通过文件读写的方式,自己实现一个函数,实现文件的拷贝功能。

代码如下:
  1.         ifstream ifs;
  2.         ifs.open("d:\\123.txt");
  3.         if (!ifs) return 0;
  4.         ifs.seekg(0,ios::end);  //将文件指针指到文件尾
  5.         int file_len;
  6.         file_len = ifs.tellg();  //计算文件字节数

  7.         char * buff = new char[file_len];  //根据文件大小建立一个内存缓存空间并赋值给指针buff
  8.         ifs.seekg(0);                                           //将文件指针设置为从头开始
  9.        
  10.         ifs.read(buff, file_len);                  //根据文件大小以二进制方式读取文件到缓存
  11.         cout << buff << endl;

  12.         ofstream ofs;
  13.         ofs.open("d:\\234.txt");          //打开写入文件  
  14.         if (!ofs) return 0;

  15.         ofs.write(buff,file_len);        //将缓存中的内容写入文件

  16.         ifs.close();
  17.         ofs.close();
  18.         delete[]buff;                //关闭文件流,并释放内存空间
复制代码


执行后,新的文件234.txt会比原来的文件123.txt多出5个字节,如下图,请问是什么原因?
《实用C++》第45课文件指针小作业执行代码后,为什么会多出5个字节?




最佳答案
78_avatar_small
2019-11-2 12:22:04
本帖最后由 muye12921 于 2019-11-2 12:49 编辑

我和你的实现方式有点区别,使用的是二进制读写的方式,当初做的时候试了下,不会出现多了字节的情况,你的方法是动态在堆上分配内存,对小文件的拷贝还行,大文件有问题,至于字节数问题,还没仔细研究,估计和使用字符读写有关系,可以改成二进制读写试试
  1. void file_copy(const char* source, const char* dest)
  2. {
  3.         ifstream fs_read(source, ios::binary);
  4.         ofstream fs_write(dest, ios::binary);

  5.         char buff[100] = { 0 };
  6.         streamsize len = 0;

  7.         if (fs_read && fs_write) {
  8.                 while (fs_read.read(buff, 100), len = fs_read.gcount()) {
  9.                         fs_write.write(buff, len);
  10.                 }
  11.         }

  12.         fs_write.close();
  13.         fs_read.close();

  14. }
复制代码




上一篇:MFC UI使用怎么那么难。
下一篇:c++ ide的区别
78_avatar_middle
最佳答案
1 
在线会员 发表于 2019-11-2 12:22:04 | 显示全部楼层    本楼为最佳答案   
bestAnswer
本帖最后由 muye12921 于 2019-11-2 12:49 编辑

我和你的实现方式有点区别,使用的是二进制读写的方式,当初做的时候试了下,不会出现多了字节的情况,你的方法是动态在堆上分配内存,对小文件的拷贝还行,大文件有问题,至于字节数问题,还没仔细研究,估计和使用字符读写有关系,可以改成二进制读写试试
  1. void file_copy(const char* source, const char* dest)
  2. {
  3.         ifstream fs_read(source, ios::binary);
  4.         ofstream fs_write(dest, ios::binary);

  5.         char buff[100] = { 0 };
  6.         streamsize len = 0;

  7.         if (fs_read && fs_write) {
  8.                 while (fs_read.read(buff, 100), len = fs_read.gcount()) {
  9.                         fs_write.write(buff, len);
  10.                 }
  11.         }

  12.         fs_write.close();
  13.         fs_read.close();

  14. }
复制代码

评分

参与人数 2驿站币 +4 热心值 +4 收起 理由
58_avatar_small thzzl + 2 + 2 很给力!
81_avatar_small Debug + 2 + 2 赞一个!

查看全部评分

81_avatar_middle
最佳答案
3 
online_supermod 发表于 2019-11-2 21:27:53 | 显示全部楼层
muye12921 发表于 2019-11-2 12:22
我和你的实现方式有点区别,使用的是二进制读写的方式,当初做的时候试了下,不会出现多了字节的情况,你的 ...

@muye12921 的方法确实更好,效率更高,而且大文件的话也不会出现一下子申请很大内存的问题,赞一个
63_avatar_middle
最佳答案
1 
ico_lz  楼主| 发表于 2019-11-5 16:39:03 | 显示全部楼层
但是你这里有设置了缓存大小才100个字节,char buff[100]  ,如果输入的拷贝文件超过100字节的话,不会溢出吗?
78_avatar_middle
最佳答案
1 
在线会员 发表于 2019-11-5 17:43:41 | 显示全部楼层
本帖最后由 muye12921 于 2019-11-5 18:29 编辑

当然不会,这里设置成100个字节还是更多的字节都无所谓,看自己取舍。这里缓存的大小只会影响循环的次数,并不会造成内存溢出。这个方法的关键在于通过循环一次读取一部分数据到缓存,再将缓存的数据写入目标文件,这里len=fs_read.gcount()为每次实际读取的字节数,也是每次要写入的字节数,这样就保证了目标文件和原文件的大小一致,当fs_read.gcount()为0,循环结束,表示文件已读取完毕。
33_avatar_middle
最佳答案
0 
在线会员 发表于 2020-8-11 19:54:06 | 显示全部楼层
#include <iostream>
#include <fstream>
using namespace std;
int main()
{
        ifstream ifs("e:\\123.txt",ios::binary);
//        ifs.open();
        if (!ifs) return 0;
        ifs.seekg(0,ios::end);  //将文件指针指到文件尾
        int file_len=0;
        file_len = ifs.tellg();  //计算文件字节数
       
        char * buff = new char[file_len+1];  //根据文件大小建立一个内存缓存空间并赋值给指针buff
        ifs.seekg(0);                     //将文件指针设置为从头开始
       
        ifs.read(buff, file_len);                  //根据文件大小以二进制方式读取文件到缓存
        buff[file_len] = '\0';
        cout << buff << endl;
       
        ofstream ofs("e:\\456.txt",ios::binary);
//        ofs.open("e:\\456.txt");          //打开写入文件
        if (!ofs) return 0;
       
        ofs.write(buff,file_len);        //将缓存中的内容写入文件
       
        ifs.close();
        ofs.close();
        delete[]buff;                //关闭文件流,并释放内存空间

        return 0;
}
33_avatar_middle
最佳答案
0 
在线会员 发表于 2020-8-12 20:27:24 | 显示全部楼层
#include <iostream>
#include <fstream>
using namespace std;

void file_copy(const char* source,const char* dest)
{
        ifstream fin;
        fin.open(source);
        if(!fin.is_open())
        {
                cout<<"要复制的文件不存在。"<<endl;
                exit(1);       
        }

        ofstream fout;
        fout.open(dest);
        if(!fout.is_open()) exit(1);
       
        char ch;
        while(fin.get(ch))
//        while((ch=fin.get() != EOF)
        {
                cout<<ch;
                fout<<ch;
        }

        fin.close();
        fout.close();
}

int main()
{
        file_copy("d:\\123.txt","d:\\456.txt");
       
        return 0;
}
您需要登录后才可以回帖 登录 | 加入驿站 qq_login

本版积分规则

×【发帖 友情提示】
1、请回复有意义的内容,请勿恶意灌水;
2、纯数字、字母、表情等无意义的内容系统将自动删除;
3、若正常回复后帖子被自动删除,为系统误删的情况,请重新回复其他正常内容或等待管理员审核通过后会自动发布;
4、感谢您对VC驿站一如既往的支持,谢谢合作!

关闭

站长提醒上一条 /2 下一条

QQ|小黑屋|手机版|VC驿站 ( 辽ICP备09019393号 )|网站地图wx_jqr

GMT+8, 2020-12-5 07:21

Powered by CcTry.CoM

© 2009-2020 cctry.com

快速回复 返回顶部 返回列表