我先用WriteFile写入数据,再重新打开程序读取数据发现只读取了部分数据?
CtestDlg::OnInitDialog()代码: CString str1,strPath;
WCHAR lpBuffer[MAX_PATH];
GetCurrentDirectory(MAX_PATH,lpBuffer);
strPath.Format(_T("%s"),lpBuffer);
AfxMessageBox(strPath);
str1+=strPath+_T("\\avaliable.db"); hFileAble=CreateFile(str1,GENERIC_READ | GENERIC_WRITE,FILE_SHARE_READ | FILE_SHARE_WRITE,NULL,
OPEN_ALWAYS,FILE_ATTRIBUTE_NORMAL,NULL);
if(INVALID_HANDLE_VALUE==hFileAble)
{
strPath.Format(_T("创建文件失败:%d"),GetLastError());
AfxMessageBox(strPath);
return FALSE;
}
写入数据代码:

        DWORD dwWritten;
CCar tempClass1;
tempClass1.m_dMiles=1111;
tempClass1.m_strID=_T("新年快乐");
tempClass1.m_dTraveled=0;
tempClass1.m_strRentDate=_T("1");
tempClass1.m_strRTNDate=_T("1");
tempClass1.next=NULL;
WriteFile(hFileAble,&tempClass1,sizeof(CCar),&dwWritten,NULL);
WriteFile(hFileAble,&tempClass1,sizeof(CCar),&dwWritten,NULL);
WriteFile(hFileAble,&tempClass1,sizeof(CCar),&dwWritten,NULL);
FlushFileBuffers(hFileAble); DWORD dwRead;
Sleep(100);
CString str1;
CCar tempClass2,tempClass3,*tempClass4;
tempClass4=new CCar();
SetFilePointer(hFileAble,0,0,FILE_BEGIN);
ReadFile(hFileAble,&tempClass2,sizeof(CCar),&dwRead,NULL);
ReadFile(hFileAble,&tempClass3,sizeof(CCar),&dwRead,NULL);
ReadFile(hFileAble,tempClass4,sizeof(CCar),&dwRead,NULL); str1.Format(_T("LastError:%d"),GetLastError());
MessageBox(str1);
str1.Format(_T("%f\n%s"),tempClass2.m_dMiles,tempClass2.m_strID);
MessageBox(str1);
str1.Format(_T("%f\n%s"),tempClass3.m_dMiles,tempClass3.m_strID);
MessageBox(str1);
str1.Format(_T("%f\n%s"),tempClass4->m_dMiles,tempClass4->m_strID);
MessageBox(str1);
CloseHandle(hFileAble);
读取数据代码:
DWORD dwRead;
Sleep(100);
CString str1;
CCar tempClass2,tempClass3,*tempClass4;
tempClass4=new CCar();
SetFilePointer(hFileAble,0,0,FILE_BEGIN);
ReadFile(hFileAble,&tempClass2,sizeof(CCar),&dwRead,NULL);
ReadFile(hFileAble,&tempClass3,sizeof(CCar),&dwRead,NULL);
ReadFile(hFileAble,tempClass4,sizeof(CCar),&dwRead,NULL); str1.Format(_T("LastError:%d"),GetLastError());
MessageBox(str1);
str1.Format(_T("%f\n%s"),tempClass2.m_dMiles,tempClass2.m_strID);
MessageBox(str1);
str1.Format(_T("%f\n%s"),tempClass3.m_dMiles,tempClass3.m_strID);
MessageBox(str1);
str1.Format(_T("%f\n%s"),tempClass4->m_dMiles,tempClass4->m_strID);
MessageBox(str1);
CloseHandle(hFileAble);
CCar类如下:
class CCar
{
public:
CCar(void);
~CCar(void);
public:
CString m_strID;
double m_dMiles;
double m_dTraveled;
CString m_strRTNDate;
CString m_strRentDate;
CCar   *next;
};
//还有个错误在执行完相应全部代码段后就是:test.exe 中的 0x5cd37321 (mfc90ud.dll) 处未处理的异常: 0xC0000005: 读取位置 0xfeeefeee 时发生访问冲突filecmfc

解决方案 »

  1.   

    读取错误是因为temp4是指针,没有能容纳结构体的空间。cstring类也不能这样直接文件io,用字符数组代替
      

  2.   

    哦不对,你分配空间了,看岔了sorry
      

  3.   

    剩下的就是cstring了,不能直接文件io,因为cstring的字符串部分实际是动态分配的,cstring类中只存了个指针
      

  4.   

    其实我可以很认真的告诉你把tempClass4相关代码注释,并删除文件,重新来过也是错的。
    其实你也可以试下,这个程序也只是我的测试程序就一个对话框程序两个按钮,一个写,一个读。
      

  5.   

    CString 对象, 不能通过 read 回来的 数据 直接构造。
    应该:
    char tmp[sizeof(car)];
    read 数据到 tmp;
    再 逐个 赋值
      

  6.   

    能说说具体怎么赋值么?强制类型转换?转成CCar类?
      

  7.   

    主要是那个 CString ,不同的值将使sizeof(car) 不同。
    你 自己试试  
      

  8.   

    CString的文件存储只能自己实现
    写文件时可以先保存字符串长度,再保存字符串文本
    读文件时先读出字符串长度,new一块数组,再按长度读字符串文本到数组,然后再赋值到Cstring或者就直接用MFC的序列化
      

  9.   

    其实你那个car 不用CStriong 用 TCHAR (如【10】)更好
      

  10.   

    你要是改成多字节应该没问题,现在是UNICODE,应该是sizeof取错了字节数,你先用数字指定固定字节数写文件试试,把所有的sizeof变成你自己计算出来的字节数
      

  11.   

    用序列化的方式,有很多现成的可以使用
    class CCar
    {
    public:
      CCar(void) : m_dMiles(0), m_dTraveled(0), next(NULL)
      {    
      }  virtual ~CCar(void)
      {
        if(next)
        {
          delete next;
          next = NULL;
        }
      }public:
      CString m_strID;
      double m_dMiles;
      double m_dTraveled;
      CString m_strRTNDate;
      CString m_strRentDate;
      CCar   *next;public:
      virtual BOOL operator == (CCar &Ob)
      {
        if(m_strID == Ob.m_strID
          && m_dMiles == Ob.m_dMiles
          && m_dTraveled == Ob.m_dTraveled
          && m_strRTNDate == Ob.m_strRTNDate
          && m_strRentDate == Ob.m_strRentDate)
        {
          if((next==NULL && Ob.next == NULL) || (*next == *Ob.next))
            return TRUE;
        }
        return FALSE;
      }  friend CArchive& operator << ( CArchive& ar, CCar &Ob)
      {     
        ar << Ob.m_strID;
        ar << Ob.m_dMiles;
        ar << Ob.m_dTraveled;
        ar << Ob.m_strRTNDate;
        ar << Ob.m_strRentDate;
        ar << (Ob.next ? true:false);
        if(Ob.next)
          ar << *Ob.next;
        return ar;
      }  friend CArchive& operator >> ( CArchive& ar, CCar &Ob)
      {
        bool bWithNext;
        ar >> Ob.m_strID;
        ar >> Ob.m_dMiles;
        ar >> Ob.m_dTraveled;
        ar >> Ob.m_strRTNDate;
        ar >> Ob.m_strRentDate;
        ar >> bWithNext;
        if(bWithNext)
        {
          Ob.next = new CCar;
          ar >> *Ob.next;
        }
        return ar;
      }};//测试代码  
    {  
      CString szFileName = _T("d:\\temp\\testCar.txt");  CCar testCar, testCar2;
      testCar.m_strID = _T("1234");
      testCar.next = new CCar;
      testCar.next->m_strID = _T("5678");
        
      try
      {
        //store
        {
          CFile file(szFileName, CFile::modeCreate|CFile::modeWrite);
          CArchive ar(&file, CArchive::store);
          ar << testCar;
          ar.Close();
          file.Close();  
        }    //load
        {
          CFile file(szFileName, CFile::modeRead);
          CArchive ar(&file, CArchive::load);
          ar >> testCar2;
          ar.Close();
          file.Close();
        }    ASSERT(testCar2 == testCar);
      }
      catch(CFileException *e)
      {
        e->ReportError();
        e->Delete();    
      }
    }