MFC中怎样在文件末尾追加数据?

糊糊 2004-09-19 01:37:47
我使用了CEditView作为我的视图.
文档序列化,调用了CEditView的SerializeRaw(ar)进行读写文本(MFC默认代码)
void CGetwordDoc::Serialize(CArchive& ar)
{
// CEditView contains an edit control which handles all serialization
((CEditView*)m_viewList.GetHead())->SerializeRaw(ar);
}
我的目标是在用SerializeRaw(ar)写文件之前,是否能够把文件的打开模式改为追加?如果能够,又如何修改呢?
谢谢大家~~!!
...全文
739 13 打赏 收藏 转发到动态 举报
写回复
用AI写文章
13 条回复
切换为时间正序
请发表友善的回复…
发表回复
糊糊 2004-09-20
  • 打赏
  • 举报
回复
恭喜还太早啊~~~

你也许就会发现,你输入12345678(随便什么文字)之后,点击保存.文件保存了!!

然后你新建,在打开你刚才保存的文件,你会发现"这是追加的文字"跑到前面去了,结果就是

这是追加的文字
12345678

这怎么成了在文件首部追加啊???????????????
memory_xj 2004-09-20
  • 打赏
  • 举报
回复
不错,通过,恭喜你!
糊糊 2004-09-19
  • 打赏
  • 举报
回复
你看看我写的::
((CEditView*)m_viewList.GetHead())->SerializeRaw(ar);

if (ar.IsStoring())
{
// TODO: add storing code here
CString filename=ar.m_strFileName;
TRACE1("文件名是%s",filename);
//ar.Flush(); //在GetFile()之前应该Flush()

CFile *pfile=ar.GetFile();
ASSERT(pfile);

pfile->Open(filename,CFile::modeReadWrite
|CFile::modeNoTruncate);

pfile->SeekToEnd(); //文件末尾
char* buf= "这是追加的文字";
pfile->Write(buf,strlen(buf));
//pfile->Close();
//----------------------------
//文件最后不关闭!!!!
//因为在ReleaseFile(pFile, FALSE);<<<<<<<<<<<(3)处
//关闭文件!!
//ReleaseFile(pFile, FALSE);在加载文件的时候也会调用的,
//所以不需要pfile->Close();
}
else
{
// TODO: add loading code here
}


糊糊 2004-09-19
  • 打赏
  • 举报
回复
我知道,我还在测试,还没有完呢.
如果你pfile->Open(filename,CFile::modeReadWrite|CFile::modeNoTruncate);前不将pfile关闭,在pfile->seekToEnd();这一句时,就会出断言错误,跟踪进去,

确实会出现断言错误!
但是我把前面的ar.Flush()注释掉了之后就没有了,原因还不清楚.

你说的方法,在我这里确实出错了,最后一句真的不能够关闭的~~~

memory_xj 2004-09-19
  • 打赏
  • 举报
回复
哈哈,抱歉!测试环境不一样~~~,你是在用保存按钮测试,而我是用打开按钮测试的。虽然功能实现了,但我的方式有问题。你们继续讨论吧!
memory_xj 2004-09-19
  • 打赏
  • 举报
回复
呵呵,我也搞不清楚了,其实我贴的代码都是通过自己测试完全实现了在末尾添加功能的。在测试中,如果你pfile->Open(filename,CFile::modeReadWrite|CFile::modeNoTruncate);前不将pfile关闭,在pfile->seekToEnd();这一句时,就会出断言错误,跟踪进去,是
LONG CFile::Seek(LONG lOff, UINT nFrom)
{
ASSERT_VALID(this);
ASSERT(m_hFile != (UINT)hFileNull); //这一句出现断言错误!我想意思挺明白的
.....
}
就说这么多了^-^
糊糊 2004-09-19
  • 打赏
  • 举报
回复
首先,感谢 memory_xj(青蛙)的回答.
下面是我的测试:使用青蛙的代码,仍然是那个错误!
我跟踪调试了一下,发现CDocument::OnSaveDocument(LPCTSTR lpszPathName)中,

BOOL CDocument::OnSaveDocument(LPCTSTR lpszPathName)
{
CFile* pFile = NULL;
pFile = GetFile(lpszPathName, CFile::modeCreate |
CFile::modeReadWrite | CFile::shareExclusive, &fe);

if (pFile == NULL)
{
...
}

CArchive saveArchive(pFile, CArchive::store|CArchive::bNoFlushOnDelete);
saveArchive.m_pDocument = this;
saveArchive.m_bForceFlat = FALSE;
Serialize(saveArchive); // save me<<<<<<<<<<<<(1)处
saveArchive.Close(); <<<<<<<<<<<(2)处
ReleaseFile(pFile, FALSE);<<<<<<<<<<<(3)处
....}

(1)处调用了void CGetwordDoc::Serialize(CArchive& ar)
{
CString filename=ar.m_strFileName;
TRACE1("文件名是",filename);
....

如果像青蛙说的那样,就还是会出错.
关键在于(2)处关闭档案,(3)处才关闭文件.
我们在(1)处最后一句话中,有pfile->Close(),就已经把文件给关闭了!!!!!!!
这才是关键所在!!!


通过我的测试,"pfile->Close(); //!!!!!先将文件关闭,关键"这一句,
一定不能够要的,否则就是覆盖文件.去掉之后才能够在文件末尾追加!!

而ar.Flush(); //在GetFile()之前应该Flush()
是可有可无的~~~~~

所以正确的应该是(我这里调试通过,并且实现了目标的代码)
CString filename=ar.m_strFileName;
TRACE1("文件名是%s",filename);
//ar.Flush(); //在GetFile()之前应该Flush()

CFile *pfile=ar.GetFile();
ASSERT(pfile);

pfile->Open(filename,CFile::modeReadWrite
|CFile::modeNoTruncate);

pfile->SeekToEnd(); //文件末尾
char* buf= "这是追加的文字";
pfile->Write(buf,strlen(buf));
//文件最后不关闭!!!!
//因为在ReleaseFile(pFile, FALSE);<<<<<<<<<<<(3)处
//关闭文件!!

欢迎大家提意见探讨....

wonhao 2004-09-19
  • 打赏
  • 举报
回复
up
memory_xj 2004-09-19
  • 打赏
  • 举报
回复
你错误在于,程序进入Serialize(CArchive& ar)时,文件已经打开了,你又打开相同文件,肯定出错了。你应该先Close(),再打开就可以了,这样:
CString filename=ar.m_strFileName;
TRACE1("文件名是%s",filename);
ar.Flush(); //在GetFile()之前应该Flush()
CFile *pfile=ar.GetFile();
ASSERT(pfile);
pfile->Close(); //!!!!!先将文件关闭,关键
pfile->Open(filename,CFile::modeNoTruncate|CFile::modeReadWrite);
pfile->SeekToEnd(); //文件末尾
char* buf= "这是追加的文字";
pfile->Write(buf,strlen(buf));
pfile->Close();
gooyan 2004-09-19
  • 打赏
  • 举报
回复
加上CFile::modeNoTruncate,不然文件会被截断得
skychild 2004-09-19
  • 打赏
  • 举报
回复
pfile->Open(filename,CFile::modeRead|CFile::modeReadWrite|CFile::modeNoTruncate);这样就不会覆盖了.
加上CFile::modeNoTruncate就行
糊糊 2004-09-19
  • 打赏
  • 举报
回复
我的意思就是选择一个已经存在的文本文件,对它进行追加.
糊糊 2004-09-19
  • 打赏
  • 举报
回复
参照网上的一些资料我把CGetwordDoc::Serialize改成了下面的这个样子,编译通过了.调试运行的时候,出错了!!
错误出现在pfile->Close()这个地方~~~~
void CFile::Close()
{
ASSERT_VALID(this);
ASSERT(m_hFile != (UINT)hFileNull);<<<<<<<<<调试错误出现之处
断言失败!!!!!!!!!!!
断言失败!!!!!!!!!!!
断言失败!!!!!!!!!!!
------------------------------------------------


void CGetwordDoc::Serialize(CArchive& ar)
{
CString filename=ar.m_strFileName;
TRACE1("文件名是%s",filename);
CFile *pfile=ar.GetFile();
ASSERT(pfile);
pfile->Open(filename,CFile::modeNoTruncate|CFile::modeReadWrite);
pfile->SeekToEnd(); //文件末尾
char* buf= "这是追加的文字";
pfile->Write(buf,strlen(buf));
pfile->Close();

// CEditView contains an edit control which handles all serialization
//((CEditView*)m_viewList.GetHead())->SerializeRaw(ar);
}
------------------------------------------
另外还有一个问题,就是在弹出保存文件对话框的时候,选择一个已经存在的文件时,会弹出文件已存在,要覆盖它吗?的提示.我知道这是默认的,但不知道怎样去掉它.注:我不想改默认的OnFileSave().

16,466

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC相关问题讨论
社区管理员
  • 基础类社区
  • Web++
  • encoderlee
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

        VC/MFC社区版块或许是CSDN最“古老”的版块了,记忆之中,与CSDN的年龄几乎差不多。随着时间的推移,MFC技术渐渐的偏离了开发主流,若干年之后的今天,当我们面对着微软的这个经典之笔,内心充满着敬意,那些曾经的记忆,可以说代表着二十年前曾经的辉煌……
        向经典致敬,或许是老一代程序员内心里面难以释怀的感受。互联网大行其道的今天,我们期待着MFC技术能够恢复其曾经的辉煌,或许这个期待会永远成为一种“梦想”,或许一切皆有可能……
        我们希望这个版块可以很好的适配Web时代,期待更好的互联网技术能够使得MFC技术框架得以重现活力,……

试试用AI创作助手写篇文章吧