Ecrire et lire des objets dans un fichier binaire. [Résolu]

cs_LA_Tupac 305 Messages postés jeudi 29 avril 2004Date d'inscription 18 janvier 2012 Dernière intervention - 16 août 2011 à 20:45 - Dernière réponse : cs_LA_Tupac 305 Messages postés jeudi 29 avril 2004Date d'inscription 18 janvier 2012 Dernière intervention
- 17 août 2011 à 20:31
Salut à tous! J'ai bien cherché mais pas trouvé de réponse dans ces forums. En C++ il est possible de sauvegarder l'instance d'une class en la castant en char* (ou byte* c'est pareil).
En code managé, j'ai l'impression que c'est différent... En tout cas StreamWriter.Write() ne fonctionne pas avec un objet en direct
Alors j'ai besoin d'un petit briefing sur le sujet
Merci d'avance.
Afficher la suite 

Votre réponse

7 réponses

cs_LA_Tupac 305 Messages postés jeudi 29 avril 2004Date d'inscription 18 janvier 2012 Dernière intervention - 16 août 2011 à 23:02
+3
Utile
En fait il suffit d'avoir les mots qui vont bien
Cela s'appelle Sérialisation en C# Et le p'tit tuto EN
Merci quand-même
@++
Cette réponse vous a-t-elle aidé ?  
Commenter la réponse de cs_LA_Tupac
krimog 1863 Messages postés lundi 28 novembre 2005Date d'inscription 14 février 2015 Dernière intervention - 17 août 2011 à 14:25
+3
Utile
Prenons un exemple :

Imaginons que le nombre enregistré dans ton fichier soit un ushort de valeur 61455.
Il s'écrit donc en binaire 11110000 00001111 (l'espace est pour différencier les 2 octets (bytes) de ton ushort).
On commence par mettre val à la valeur 0
val : 00000000 00000000
Puis on lit le premier octet de ta donnée : 11110000 (240)
On ajoute cet octet DÉPLACÉ DE 8 BITS à gauche, soit 11110000 00000000, à val.
val : 11110000 00000000
Enfin, on lit le byte (octet) suivant : 00001111 (15)
Et on ajoute cette valeur à val.
val : 11110000 00001111
Donc val fait bien la bonne valeur.

En revanche, une petite erreur s'est glissée dans mon code : je le suis planté dans le cast :
val += (ushort)(tmpByte << 8);
(ushort)tmpByte;


Krimog : while (!(succeed = try())) ;
- Nous ne sommes pas des décodeurs ambulants. Le style SMS est prohibé. -
Cette réponse vous a-t-elle aidé ?  
Commenter la réponse de krimog
cs_LA_Tupac 305 Messages postés jeudi 29 avril 2004Date d'inscription 18 janvier 2012 Dernière intervention - 17 août 2011 à 00:15
0
Utile
Erf je suis moins optimiste maintenant
Je ne pense pas que ce soit compatible: lors de la lecture du ushort du headersize, le BinaryFormatter.Deserialize() crash et au bout de la pile d'appel j'ai:
System.Runtime.Serialization.Formatters.Binary.__BinaryParser.ReadSerializationHeaderRecord (Parameters=) in 

Serialisationheader !! il y'a peut être plus qu'un dump mémoire->fichier

je précise la structure du début de fichier:
char[64]|ushort|ushort|....

Voila le bout de code qui crash:
ushort HeaderSize;
Stream stream = File.Open(filename, FileMode.Open);
stream.Seek(64,0); //pas sûr pour le 0
      	BinaryFormatter bFormatter = new BinaryFormatter();
      	HeaderSize = (ushort)bFormatter.Deserialize(stream);//Crash!

Merci.
Commenter la réponse de cs_LA_Tupac
krimog 1863 Messages postés lundi 28 novembre 2005Date d'inscription 14 février 2015 Dernière intervention - 17 août 2011 à 10:15
0
Utile
Salut

La sérialisation sur une classe fait bien plus qu'un dump mémoire. En effet, le principe de la sérialisation, c'est d'obtenir des données indépendantes de l'emplacement mémoire.
Pour cela, il est obligé de récupérer toutes les références de manière récursive afin de les intégrer à la structure sérialisée.

En revanche, dans le code que tu donnes, ce n'est pas la sérialisation que tu dois utiliser.
En gros, la sérialisation, tu ne dois pas te poser de question sur la structure de ton fichier, car le framework sérialise "à sa guise" ta/tes classe(s).
En gros, c'est vraiment :
jeSerialiseDansMonFichier(monObjet);

et
monObjet = (maClasse)jeDeserialseDepuisMonFichier();

Il ne faut pas chercher plus loin dans l'utilisation.

Si tu veux lire ton ushort, il vaut mieux le faire manuellement (pas testé, mais ça devrait marcher) :
Stream stream = File.Open(filename, FileMode.Open);
stream.Seek(64, SeekOrigin.Begin);
ushort val = 0;
int tmpByte = stream.ReadByte();
val += ((byte)tmpByte) << 8; // On décale de 8 bits vers la gauche
tmpByte = stream.ReadByte();
val += (byte)tmpByte;
stream.Close();


Krimog : while (!(succeed = try())) ;
- Nous ne sommes pas des décodeurs ambulants. Le style SMS est prohibé. -
Commenter la réponse de krimog
cs_LA_Tupac 305 Messages postés jeudi 29 avril 2004Date d'inscription 18 janvier 2012 Dernière intervention - 17 août 2011 à 12:50
0
Utile
Ok merci c'est bien ce que je pensai...
J'ai essayé ton bout de code mais je vois pas en quoi l'ajout des deux bytes donnerai le nombre sur 16bits...
En tout cas il y'a un soucis de cast int->ushort à la 5ème ligne que je résous en changeant le type de val et en mode débug je n'arrive pas a évaluer val.... le résultat n'est pas bon c'est sur..
Commenter la réponse de cs_LA_Tupac
cs_LA_Tupac 305 Messages postés jeudi 29 avril 2004Date d'inscription 18 janvier 2012 Dernière intervention - 17 août 2011 à 14:34
0
Utile
Ok une simple erreur de syntaxe donc. Merci je comprend mieux. Je test ça après le taf et je te tiens au jus.
Merci encore
Commenter la réponse de cs_LA_Tupac
cs_LA_Tupac 305 Messages postés jeudi 29 avril 2004Date d'inscription 18 janvier 2012 Dernière intervention - 17 août 2011 à 20:31
0
Utile
Ok j'ai compris et c'est pas banal
en fait les données de mon fichier sont écrites à l'envers . le ushort 4336 par ex, vaut 10F0h et il est écrit F010h !! Je n'ai aucune idée du pourquoi mais pour info, l'écriture en cpp des données en question se fait par un simple
ofstream.write((char*)monshort, sizeof(short);

Si un guru du cpp peut nous expliquer ça, je serai curieux d'écouter ses explications...
J'ai passé 1 heure a décortiquer ma base en hexa pour découvrir ça et maintenant je dois faire de même pour mes class dumpées à l'envers !!
Bon j'aime bien me faire plaindre mais au boulot !
et merci à toi surtout
Commenter la réponse de cs_LA_Tupac

Vous n'êtes pas encore membre ?

inscrivez-vous, c'est gratuit et ça prend moins d'une minute !

Les membres obtiennent plus de réponses que les utilisateurs anonymes.

Le fait d'être membre vous permet d'avoir un suivi détaillé de vos demandes et codes sources.

Le fait d'être membre vous permet d'avoir des options supplémentaires.