Enregistrement avec Serialize et l'opérateur <<

Enregistrement avec Serialize et l'opérateur << - C++ - Programmation

Marsh Posté le 06-07-2004 à 16:03:34    

Bonjour à tous,
J'ai créé une application windows permettant de gérer des documents et maintenant j'aimerais enregistrer les données puis les réouvrir. Le problème est que quand j'ouvre le fichier sauvegardé, j'obtiens un message d'erreur système.
De plus, si je sauvegarde des int, des float, y'a pas de problème pour les charger par contre si j'essais de sauvegarder un type CString en utilisant la fonction WriteString de la classe Serialize, là ça fait des dégats. Est-ce que quelqu'un sait comment faire.

Reply

Marsh Posté le 06-07-2004 à 16:03:34   

Reply

Marsh Posté le 07-07-2004 à 12:06:07    

Désolé d'insister mais c'est assez important. Taz, peut-être que tu pourrais m'aider vu que tu as l'air d'être le meilleur?

Reply

Marsh Posté le 07-07-2004 à 12:23:09    

1 - Taz ne te répondra pas car tu sembles utiliser les MFC, et c'est pas trop son truc :D
2 - Je veux bien essayer de t'aider si tu postes le code qui plante, sinon je vois mal comment on pourrait deviner la cause de ton erreur


---------------
J'ai un string dans l'array (Paris Hilton)
Reply

Marsh Posté le 07-07-2004 à 12:39:06    

OK. Voici le code de toute ma classe CFEATDoc, comme ça si le problème vient d'ailleurs, vous pourrez peut-être le trouver.

Code :
  1. // F.E.A.TDoc.cpp : implémentation de la classe CFEATDoc
  2. //
  3. #include "stdafx.h"
  4. #include "F.E.A.T.h"
  5. #include "Interface.h"
  6. #include "Dialog_Options.h"
  7. #include "F.E.A.TDoc.h"
  8. #include ".\f.e.a.tdoc.h"
  9. #ifdef _DEBUG
  10. #define new DEBUG_NEW
  11. #endif
  12. #include <malloc.h>
  13. class CInterface;
  14. extern CInterface *Interface;
  15. // CFEATDoc
  16. IMPLEMENT_DYNCREATE(CFEATDoc, CDocument)
  17. BEGIN_MESSAGE_MAP(CFEATDoc, CDocument)
  18. END_MESSAGE_MAP()
  19. // construction ou destruction de CFEATDoc
  20. CFEATDoc::CFEATDoc()
  21. {
  22. // TODO : ajoutez ici le code d'une construction unique
  23. }
  24. CFEATDoc::~CFEATDoc()
  25. {
  26. }
  27. BOOL CFEATDoc::OnNewDocument()
  28. {
  29. if (!CDocument::OnNewDocument())
  30.  return FALSE;
  31. // TODO : ajoutez ici le code de réinitialisation
  32. // (les documents SDI réutiliseront ce document)
  33. CDialog_Options dlg;
  34. int OK;
  35. char Caption_Edit[30];
  36. //Charge les options
  37. OK=dlg.Chargement_Options("[Durée du test]",&Interface->Options.DUREE_def_HH,&Interface->Options.DUREE_def_MM,&Interface->Options.DUREE_def_SS);
  38. if(OK!=0)
  39. {
  40.  dlg.Chargement_Options("[Titre]",&Interface->Options.TITRE_def);
  41. }
  42. //Interface->OnInitialUpdate();
  43. //Initialise le texte des boutons
  44. LoadString(GetModuleHandle(NULL),TXT_Edit,Caption_Edit,30);
  45. Interface->m_Ctrl_Furet_1.SetWindowText(Caption_Edit);
  46. Interface->m_Ctrl_Furet_2.SetWindowText(Caption_Edit);
  47. Interface->m_Ctrl_Furet_3.SetWindowText(Caption_Edit);
  48. Interface->m_Ctrl_Furet_4.SetWindowText(Caption_Edit);
  49. Interface->Nb_File_Genere=0; //Aucun fichier généré pour l'instant
  50. Interface->Select_Range=1;
  51. Interface->Test.Test_Termine=FALSE; //Le test n'est pas terminé (puisqu'il n'est pas commencé)
  52. //Initialiser les valeurs des furets
  53. Interface->Init_Furet(&Interface->Furet_1);
  54. Interface->Init_Furet(&Interface->Furet_2);
  55. Interface->Init_Furet(&Interface->Furet_3);
  56. Interface->Init_Furet(&Interface->Furet_4);
  57. //Initialise les images de gauche
  58. Interface->Definir_Image(&Interface->m_Image_Furet_1,IDI_Image_Info);
  59. Interface->Definir_Image(&Interface->m_Image_Furet_2,IDI_Image_Info);
  60. Interface->Definir_Image(&Interface->m_Image_Furet_3,IDI_Image_Info);
  61. Interface->Definir_Image(&Interface->m_Image_Furet_4,IDI_Image_Info);
  62. return TRUE;
  63. }
  64. // sérialisation de CFEATDoc
  65. void CFEATDoc::Serialize(CArchive& ar)
  66. {
  67. if (ar.IsStoring())
  68. {
  69.  Interface->m_Ctrl_Commentaire_Furet_1.GetWindowText(Interface->Furet_1.Caracteristiques.Commentaire); //Sauvegarde du commentaire
  70.  Enregistrer_Furets(ar, &Interface->Furet_1);
  71.  Interface->m_Ctrl_Commentaire_Furet_2.GetWindowText(Interface->Furet_2.Caracteristiques.Commentaire); //Sauvegarde du commentaire
  72.  Enregistrer_Furets(ar, &Interface->Furet_2);
  73.  Interface->m_Ctrl_Commentaire_Furet_3.GetWindowText(Interface->Furet_3.Caracteristiques.Commentaire); //Sauvegarde du commentaire
  74.  Enregistrer_Furets(ar, &Interface->Furet_3);
  75.  Interface->m_Ctrl_Commentaire_Furet_4.GetWindowText(Interface->Furet_4.Caracteristiques.Commentaire); //Sauvegarde du commentaire
  76.  Enregistrer_Furets(ar, &Interface->Furet_4);
  77.  Enregistrer_Caracteristiques_Test(ar, &Interface->Test);
  78. }
  79. else
  80. {
  81.  Charger_Furets(ar, &Interface->Furet_1);
  82.  Charger_Furets(ar, &Interface->Furet_2);
  83.  Charger_Furets(ar, &Interface->Furet_3);
  84.  Charger_Furets(ar, &Interface->Furet_4);
  85.  Charger_Caracteristiques_Test(ar, &Interface->Test);
  86. }
  87. }
  88. // diagnostics pour CFEATDoc
  89. #ifdef _DEBUG
  90. void CFEATDoc::AssertValid() const
  91. {
  92. CDocument::AssertValid();
  93. }
  94. void CFEATDoc::Dump(CDumpContext& dc) const
  95. {
  96. CDocument::Dump(dc);
  97. }
  98. #endif //_DEBUG
  99. // commandes pour CFEATDoc
  100. void CFEATDoc::Enregistrer_Furets(CArchive& ar, FURET *furet)
  101. {
  102. int i;
  103. ar << furet->num_element;
  104. for(i=0 ; i<furet->num_element ; i++)
  105. {
  106.  ar << furet->Donnees[i].Nb_Retch;
  107.  ar << furet->Donnees[i].Nb_Vomit;
  108.  ar << furet->Donnees[i].Erreur;
  109.  ar << furet->Donnees[i].Temps_Debut_Phase;
  110.  ar << furet->Donnees[i].Temps_Fin_Phase;
  111. }
  112. ar << (long)furet->Caracteristiques.Debut_Chrono;
  113. ar << furet->Caracteristiques.Poids;
  114. ar.WriteString(furet->Caracteristiques.Dose);
  115. ar.WriteString("\n" );
  116. ar.WriteString(furet->Caracteristiques.Identification);
  117. ar.WriteString("\n" );
  118. // Enregistrer_CString_Type(ar, furet->Caracteristiques.Commentaire);
  119. //ar.WriteString(furet->Caracteristiques.Commentaire);
  120. //ar.WriteString("\n" );
  121. }
  122. void CFEATDoc::Charger_Furets(CArchive& ar, FURET *furet)
  123. {
  124. int i;
  125. ar >> furet->num_element;
  126. furet->Donnees=(DONNEES_FURET *)malloc(sizeof(DONNEES_FURET));
  127. for(i=0 ; i<furet->num_element ; i++)
  128. {
  129.  ar >> furet->Donnees[i].Nb_Retch;
  130.  ar >> furet->Donnees[i].Nb_Vomit;
  131.  ar >> furet->Donnees[i].Erreur;
  132.  ar >> furet->Donnees[i].Temps_Debut_Phase;
  133.  ar >> furet->Donnees[i].Temps_Fin_Phase;
  134.  furet->Donnees=(DONNEES_FURET *)realloc(furet->Donnees, _msize(furet->Donnees)+sizeof(DONNEES_FURET));
  135. }
  136. ar >> (long)furet->Caracteristiques.Debut_Chrono;
  137. ar >> furet->Caracteristiques.Poids;
  138. ar.ReadString(furet->Caracteristiques.Dose);
  139. ar.ReadString(furet->Caracteristiques.Identification);
  140. // Charger_CString_Type(ar, &furet->Caracteristiques.Commentaire);
  141. // ar.ReadString(furet->Caracteristiques.Commentaire);
  142. }
  143. void CFEATDoc::Enregistrer_Caracteristiques_Test(CArchive& ar, CARACTERISTIQUE_TEST* test)
  144. {
  145. //Il faut valider les expressions avant de les sauvegarder
  146. char buffer[9];
  147. //Enregistre la duree du test
  148. ar << test->Duree_Test;
  149. //Enregistre la date
  150. _strdate(buffer);
  151. test->Date.Format(" %.2s/%.2s/%.2s",&buffer[3],&buffer[0],&buffer[6]);
  152. ar.WriteString(test->Date);
  153. ar.WriteString("\n" );
  154. //Enregistrer_CString_Type(ar, test->Date);
  155. Interface->m_Ctrl_Session.GetWindowText(test->Session);
  156. ar.WriteString(test->Session);
  157. ar.WriteString("\n" );
  158. //Enregistrer_CString_Type(ar, test->Session);
  159. Interface->m_Ctrl_Study.GetWindowText(test->Study);
  160. ar.WriteString(test->Study);
  161. ar.WriteString("\n" );
  162. //Enregistrer_CString_Type(ar, test->Study);
  163. Interface->m_Ctrl_Technicien.GetWindowText(test->Technician);
  164. ar.WriteString(test->Technician);
  165. ar.WriteString("\n" );
  166. //Enregistrer_CString_Type(ar, test->Technician);
  167. //Interface->m_Ctrl_Titre.GetWindowText(test->Titre);
  168. //ar.WriteString(test->Titre);
  169. //ar.WriteString("\n" );
  170. //Enregistrer_CString_Type(ar, test->Titre);
  171. Interface->m_Ctrl_Titre.GetWindowText(test->Titre);
  172. ar << test->Titre.GetLength();
  173. ar.Write(test->Titre, test->Titre.GetLength());
  174. }
  175. void CFEATDoc::Charger_Caracteristiques_Test(CArchive& ar, CARACTERISTIQUE_TEST* test)
  176. {
  177. //Charger_CString_Type(ar, &test->Date);
  178. //ar >> test->Duree_Test;
  179. //Charger_CString_Type(ar, &test->Session);
  180. //Charger_CString_Type(ar, &test->Study);
  181. //Charger_CString_Type(ar, &test->Technician);
  182. //Charger_CString_Type(ar, &test->Titre);
  183. int taille;
  184. ar >> test->Duree_Test;
  185. ar.ReadString((CString& )test->Date);
  186. ar.ReadString((CString& )test->Session);
  187. ar.ReadString((CString& )test->Study);
  188. ar.ReadString((CString& )test->Technician);
  189. // ar.ReadString(test->Titre); //pb: charge première ligne uniquement
  190. ar >> taille;
  191. ar.Read(&test->Titre, taille);
  192. }
  193. void CFEATDoc::Enregistrer_CString_Type(CArchive& ar, CString texte)
  194. {
  195. int i;
  196. int taille;
  197. taille=texte.GetLength();
  198. ar << taille;
  199. for(i=0 ; i<=taille ; i++)
  200.  ar << texte.GetAt(i);
  201. }
  202. void CFEATDoc::Charger_CString_Type(CArchive& ar, CString *texte)
  203. {
  204. int i;
  205. int taille;
  206. char car;
  207. ar >> taille;
  208. *texte="";
  209. for(i=0 ; i<=taille ; i++)
  210. {
  211.  ar >> car;
  212.  *texte+=car;
  213. }
  214. }


Comme vous pouvez le constater, j'ai essayé avec différentes méthodes (fonctions fournies par Visual, réécrire des fonctions d'enregistrement...). Mais ça plante quand même.

Reply

Marsh Posté le 07-07-2004 à 13:42:02    

furet->Donnees=(DONNEES_FURET *)malloc(sizeof DONNEES_FURET));
=> new
 
for i=0 ; i<furet->num_element ; i++) manque un (
ar >> (long furet->Caracteristiques.Debut_Chrono; => ?
 
le retour chariot est peut-être \r\n au lieu de \n ?


---------------
-( BlackGoddess )-
Reply

Marsh Posté le 07-07-2004 à 13:58:00    

Si tu fais new au lieu de malloc, est-ce que tu peux utiliser realloc après?
Ah oui exact, erreur de frappe c'est :

Code :
  1. ar >> (long) furet->Caracteristiques.Debut_Chrono;


(C'est bizarre que le compilo n'est rien dit!)
Qu'est-ce que tu veux dire par retour chariot? Je n'ai pas besion d'enregistrer des retours à la ligne mais j'utilise '\n' pour que la fonction ReadString() puisse ensuite lire les données ligne par ligne

Reply

Marsh Posté le 07-07-2004 à 13:59:44    

J'ai fait un copié-collé et j'ai oublié de corriger l'erreur. le code est:

Code :
  1. ar >> (long)  furet->Caracteristiques.Debut_Chrono;

Reply

Marsh Posté le 07-07-2004 à 14:04:42    

AH! Je sais pas pourquoi mais la parenthèse fermante ne passe pas! Dernière tentative, attention voici le code :

Code :
  1. ar >> (long)  furet->Caracteristiques.Debut_Chrono;

Reply

Marsh Posté le 07-07-2004 à 14:06:08    

bin peut-être que ReadString considère \r\n comme retour chariot au lieu de \n ?


---------------
-( BlackGoddess )-
Reply

Marsh Posté le 07-07-2004 à 14:06:16    

Et non ça passe pas! Bon allez, une dernière fois pour la route :

Code :
  1. ar >> (long  ) furet->Caracteristiques.Debut_Chrono;

Reply

Marsh Posté le 07-07-2004 à 14:06:16   

Reply

Marsh Posté le 07-07-2004 à 14:30:32    

Y'a un truc qui est vraiment bizarre. Lorsque je quitte mon appli, je libère la mémoire en utilisant l'instruction free(). Si je ne sauvegarde rien, y'a pas de problème, ça marche parfaitement. Maintenant, si je rajoute des instructions pour sauvegarder et ouvrir, c'est à ce moment que la désallocation dynamique déconne. Il vient de là le message d'erreur. Je comprend pas pourquoi ça dépend de la sauvegarde.
Si j'enlève les instructions permettant de libérer la mémoire, y'a plus d'erreur.
Moi pas comprendre!

Reply

Marsh Posté le 08-07-2004 à 10:06:26    

CARACTERISTIQUE_TEST* test
=> tu as définis un truc comme ca :
struct CARACTERISTIQUE_TEST
{
     int Duree_Test;  
     CString Date;  
     CString Session;  
     CString Study;  
     CString Technician;  
     CString Titre;  
};
 
?
 
si c'est le cas, et que tu l'alloue avec malloc, les constructeurs des CString ne seront pas executés ...
 
qd on dit que en C++ c'est new / delete et en C malloc / free, c pas juste pour faire joli.


---------------
-( BlackGoddess )-
Reply

Marsh Posté le 08-07-2004 à 14:06:22    

Citation :

Si j'enlève les instructions permettant de libérer la mémoire, y'a plus d'erreur.


mais ya un joli memory leak -_-

Reply

Marsh Posté le 09-07-2004 à 09:01:42    

C'est plûtot
[cpp]
struct CARACTERISTIQUE_TEST
{
    int Duree_Test;
    ...
};
 
CARACTERISTIQUES_TEST Test;


Message édité par choupinou le 09-07-2004 à 09:03:00
Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed