Vous ne trouvez pas de réponse à votre problème ? Alors posez la question dans le forum. Souvenez-vous qu'il n'y a jamais de question bête, mais rester dans l'ignorance parce que l'on n'ose pas poser une question, ça c'est une erreur !

CLIENT/SERVEUR ET PIECE JOINTE


Information sur la source

Catégorie :Réseaux & Internet Source .NET ( DotNet ) Classé sous : client, serveur, fichier, piece, jointe Niveau : Initié Date de création : 29/10/2004 Date de mise à jour : 03/11/2004 14:07:17 Vu / téléchargé: 8 989 / 1 642

Note :
10 / 10 - par 1 personne
10,00 / 10

  • 1

  • 2

  • 3

  • 4

  • 5

  • 6

  • 7

  • 8

  • 9

  • 10

Commentaire sur cette source (9)
Ajouter un commentaire et/ou une note


Description

Cliquez pour voir la capture en taille normale
Voilà il s'agit de l'évolution de la source Client et Serveur que j'ai déposée il y a quelques jours.
Je ne la mets pas à jour...Je propose ici une nouvelle source car l'évolution est majeure.

Cette applic. permet toujours de communiquer avec les utilisateurs du réseau mais en plus, elle permet de leur transmettre une pièce jointe et ce, QUELLE QUE SOIT SA TAILLE.

La réception est réalisée dans une boucle, pour réécrire le fichier joint en même temps que les paquets sont reçus.
Je transfert donc les informations du fichier par petits paquets de 2048 Octets grâce à la classe BinaryReader qui me permet de récupérer les données binaires...Je réceptionne ces paquets et je les réécris instantanément, cette fois à l'aide de la classe BinaryWriter.

Voilà, il me semble que ça fonctionne très bien...En tous cas avec tous les ordi. de mon réseau...

Laissez moi vos commentaires...
 

Conclusion

Je livre dans les sources, une solution intermédiaire qui permet de reconstruire l'exemple avec un fichier PDF très détaillé pour le pas à pas....
 

Fichier Zip

Pour les "Membres Club", vous pouvez télécharger directement un fichier contenu dans le zip sans télécharger le zip en entier !

Télécharger le zip

Historique

29 octobre 2004 18:36:22 :
Il manquait des sous dossiers dans le rep.
03 novembre 2004 12:14:14 :
Mise à jour qui prend en considération les remarques de Xya. J'ai sorti de la boucle la déclaration malencontreuse du tableau de Bytes. Le Gain en ressources CPU est loin d'être significatif. De 3% d'occupation du Proc. pendant l'envoi d'un gros fichier, je passe à 2%. Mais bon, au moins le Garbage Collector ne se déclenche pas à tout bout de champ et quoiqu'il arrive, c'est mieux... Cette nouvelle applic. gère aussi les messages mis en forme, RTF...Pas de PDF cette fois concernant cette évolution mais j'avais déposé une source sur les RichTextBox: http://www.csharpfr.com/code.aspx?ID=19662 Il y a encore beaucoup à faire et surtout à stabiliser. Il y a une petite part d'Octets "vides" perdus je ne sais où que j'écris sans le vouloir à la fin des fichiers que j'envoie (100 Octets environs), ce qui dans la majorité des cas ne pose pas de souci mais ça arrive (fichiers AVI notamment à cause de leur signature je suppose)...Tout le reste pas, il me semble. ZIPPER ==> Aucun souci.
03 novembre 2004 13:13:18 :
Changement de capture
03 novembre 2004 14:07:18 :
Capture !!

Commentaires et avis

signaler à un administrateur
Commentaire de Xya le 29/10/2004 23:23:00

Il y a je crois 2 problèmes avec l'envoi:
D'abord tu alloues pour chaque 'bloc' de 2048 octets un nouveau tableau:

while(Lecteur.Position<Lecteur.Length)
{

      byte[] tableau = new Byte[2048];
      ...
}

Je pense que tu pourrais écrire:

byte[] tableau = new Byte[2048];
while(Lecteur.Position<Lecteur.Length)
{
       ...
}

pour éviter les allocations inutiles.

Ensuite quand tu appelle ReadBytes de BinaryReader il t'alloue à chaque fois un tableau de 2048 bytes,  même problème:

while(Lecteur.Position<Lecteur.Length)
{

      byte[] tableau = new Byte[2048];
       ...
       tableau = Lire.ReadBytes(2048); //BinaryReader
       transmission.Write(tableau,0, tableau.Length);
}

En fait tu peut te passer complètement de BinaryReader:

while(Lecteur.Position<Lecteur.Length)
{
        byte[] tableau = new Byte[2048];
         ...
         Lecteur.Read( tableau, 0, tableau.Length ); //Stream
         transmission.Write(tableau,0, tableau.Length);
         ...
}

Ce qui ferait au final:

byte[] tableau = new Byte[2048];
while(Lecteur.Position<Lecteur.Length)
{
         ...
         Lecteur.Read( tableau, 0, tableau.Length ); //Stream
         transmission.Write(tableau,0, tableau.Length);
         ...
}

En ce moment je bosse aussi sur un projet qui envoie des fichiers à travers un réseau et je suis confronté au mêmes problèmes de mémoire pour les gros fichiers :)

Xya

signaler à un administrateur
Commentaire de yous le 02/11/2004 07:19:12

En ce qui concerne la déclaration du tableau de variables, tu as raison, elle doit se trouver en dehors de la boucle...

Concernant la classe BinaryReader, je ne peux pas m'en passer, c'est elle qui me permet de transmettre les fichiers par paquets, quel que soit leur type (Videos, Images...), et de les reconstituer, côté serveur avec BinaryWriter.

Personnellement, telle que je l'ai testée, l'application ne me pose aucun souci de mémoire avec les gros fichiers. J'ai fait des essais avec des fichiers de plus de 200 Mo et ça passe...

Bien sûr, je n'ai pas eu l'occasion de la tester dans tous les contextes.

signaler à un administrateur
Commentaire de Xya le 02/11/2004 15:44:00

Tu as tout à fait raison, cela ne pose pas de problème côté mémoire puisque le récupérateur de mémoire (GC) récupère la mémoire non utilisée quand il le faut, mais le GC utilise le processeur inutilement, ce qui pourrait être évité en changeant juste deux lignes de ton programme.
D'ailleurs, utiliser FileStream plutôt que BinaryReader marche tout aussi bien.


Pour montrer l'utilisation excessive du GC, j'ai utilisé CLR Profiler (http://www.microsoft.com/downloads/details.aspx?FamilyId=86CE6052-D7F4-4AEB-9B7A-94635BEEBDDA&displaylang=en)
qui enregistre entre autres les allocations et des libérations de mémoire.

Utilisation de la mémoire de ton prog non modifié (la mémoire allouée pour envoyer la pièce jointe est en rouge,  chaque libération de mémoire est marquée sur l'axe horizontal (gc #x))
http://pasaulais.free.fr/yous_client_1.png


Utilisation de la mémoire de ton prog avec les deux lignes modifiées (la mémoire allouée pour envoyer la pièce jointe est cette fois en jaune)
http://pasaulais.free.fr/yous_client_2.png


Dans le premier on a plus de 500 libérations de mémoire en  
170 secondes (à peu près trois libérations par secondes) et dans le deuxième juste 6 dans le même temps.

Tout ca pour montrer à quel point ton prog pourrait profiter de changer juste 2 lignes de son code :)


Xya

signaler à un administrateur
Commentaire de yous le 02/11/2004 17:43:16

En effet la différence est saisissante. Dans le deuxième cas, le gc se déclenche pour ainsi dire presque jamais.

Très instructif ce que tu m'enseignes même s'il me semblait évident que le CPU était sur-utilisé. En revanche je ne vois pas comment palier le problème, mais toi si !!

Dans le deuxième cas, le fait que System.String prenne autant de ressources vient du fait que tu exploites FileStream au lieu de BinaryReader ? Tu stockes en masse dans un String ?

Mais quelles sont elles ces deux lignes de code ???

En tous cas, merci pour tout l'intérêt que tu portes à cette source, le temps que tu y passes et les enseignements que tu m'apportes.

Et merci particulièrement pour avoir déposé ces deux captures sur ton site perso....

signaler à un administrateur
Commentaire de Xya le 02/11/2004 19:02:17

Une chose à la fois, dans le désordre

>>Et merci particulièrement pour avoir déposé ces deux captures sur ton site perso....

En fait c'est juste un espace de stockage pour moi :)

>>Mais quelles sont elles ces deux lignes de code ???
Voir premier commentaire

byte[] tableau = new Byte[2048];
while(Lecteur.Position<Lecteur.Length)
{
         ...
         Lecteur.Read( tableau, 0, tableau.Length ); //Stream
         transmission.Write(tableau,0, tableau.Length);
         ...
}

dans Form1.cs (lignes 1068-1078 à peu près)

>>Dans le deuxième cas, le fait que System.String prenne autant de ressources vient du fait que tu exploites FileStream au lieu de BinaryReader ? Tu stockes en masse dans un String ?

En fait si on regarde les allocations pour String, on voit que ca vient de String.Concat et de Int64.ToString (http://pasaulais.free.fr/yous_client_3.png) qui viennent probablement de la ligne

etat.Panels[0].Text="Envoyés: " + Lecteur.Position.ToString() + " sur " + Lecteur.Length.ToString();

(En interne C# remplace les concaténations de chaînes avec "+" par String.Concat)

Je pense qu'une des solutions les plus rapides serait de bouger l'appel à Lecteur.Length.ToString hors de la boucle (la taille du fichier ne change pas, ca ne sert à rien d'appeler plusieurs fois ToString dessus) pour gagner vite fait 1,6 Mo de mémoire allouée.

>> En tous cas, merci pour tout l'intérêt que tu portes à cette source, le temps que tu y passes et les enseignements que tu m'apportes.

En fait je travaille sur un projet qui envoie aussi des fichiers sur un réseau (mais juste des fichiers, pas de système de messages), et donc j'ai été confronté y'a vraiment pas longtemps (genre 1-2 semaines) au problème de la mémoire, ce qui m'a amené à utiliser CLRProfiler (qui peut être comme tu as pu le voir très utile et que je te conseille d'utiliser sur tes projets les plus importants, pour avoir l'oeil à ce que fait ton programme en arrière plan). Donc si les problèmes dont je me suis sorti peuvent te faire gagner du temps et améliorer la qualité de ton prog, autant que tu en profites :)

signaler à un administrateur
Commentaire de yous le 02/11/2004 19:09:01

Comme quoi, il est important de coder propre !! Je modifie donc ces deux lignes...

J'ai récupéré l'utilitaire...que je ne connaissais pas.

Je vais donc bien sûr l'utiliser.

Merci encore pour ton aide !!

signaler à un administrateur
Commentaire de Xya le 02/11/2004 19:32:19

>> Comme quoi, il est important de coder propre !!

En fait, je crois que le plus important avec .NET c'est que ca peut vraiment t'aider à faire des trucs sympa mais que si tu ne sais pas ce que .NET fait pour toi,  ca te peut te prendre par suprise (par exemple ici sur les 1000+ lignes de ton prog, moins de 10 posaient problème pour ses performances, mais changer ce petit nombre de lignes a radicalement changé ses perfs)

>>Merci encore pour ton aide !!

De rien :)

signaler à un administrateur
Commentaire de mlabassi le 07/06/2008 16:33:48

BONJOUR,

Cette application me plait mais ne marche pas chez moi que sans debugging.
En effet il y a apparement un problème dans jecoute.stop() à l'intérieur de catch.

MERCI de me répondre.

signaler à un administrateur
Commentaire de simoait le 10/06/2008 15:45:50

bonjour j ai aussi le méme probléme dans jecoute.stop() à l'intérieur de catch. ca debug pas .

merci pour votre aide .

Ajouter un commentaire

Discussions en rapport avec ce code source dans le forum

mailto et piece jointe [ par MorpionMx ] Bonjour, Dans un controle utilisateur qui affiche un fichier texte, j'ai un bouton qui permet d'envoyer le fichier en cours d'affichage par mail.Quand Au Secours (Serveur/Client) [ par JCpp ] Sur ce site, je n'ai trouvé aucune Source Server/Client avec plusieurs Client.ci non, Je ne comprends pas pourquoi sa ne fonctionne pas, j'ai bien mi [C#] Téléchargement de fichier [ par scoubidou944 ] Autant le téléchargement d'un fichier est bête comme choux :System.Net.WebClient client = new WebClient();client.DownloadFile ("http://www.MonURL.com remoting [ par petitou ] Salut,voila ma question :Je crée un client/serveur avec .NET Remoting. J'ai 3 classes :client, serveur et remote. remote est l'objet unique instancié c# envoyer un fichier XML sur un serveur [ par Salvo ] Bonjour je suis à la recherche d'un moyen pour envoyer le contenu de fichiers XML de plusieurs clients (tous avec la même structure) ver un serveur. Vérifier un fichier sur le web [ par Ti_Math ] Bonjour je recherche une classe ou une méthode qui me permetterais de vérifier si un fichier existe sur un serveur distant.genre serveur FTP. un genre Upload de fichier sur un serveur [ par ousta ] Voila jutilise c# avec webforms et mon appli tourne sur IISjaurais aimé savoir comment je devais my prendre pour transferer un fichier sur le serveur envoyer et recevoir des fichier par un serveur. [ par gomoz ] Bonjour,j'ai programmé un premier programme en c#, un truc comme cmd.exe (j'ai réinventé l'eau chaude quoi ;)) mais maintenant je voudrai l'amméliorer Thread + NetworkStream [ par JuS ] Je vais vous exposer mon problème (c'est un peu long à lire et à comprendre...)Je programme un programme client/serveur.Le client, en C#, communique a Comparaison d'hôte pour un socket [ par Oeil_de_taupe ] Bonjour tous le mondeJe suis en train de faire joujou avec les sockets UDP. Je crée une classe qui permettra la connection entre deux sockets (UDP) av


Nos sponsors

Sondage...

CalendriCode

Décembre 2008
LMMJVSD
1234567
891011121314
15161718192021
22232425262728
293031    

Consulter la suite du CalendriCode

Téléchargements

Logiciels à télécharger sur le même thème :



Développement réalisé par Nicolas SOREL (Nix) avec l'aide de : Cyril DURAND et Emmanuel BAÏSE, Merci à Vincent pour ses précieux conseils
CodeS-SourceS.com© Toute reproduction même partielle est interdite sauf accord écrit du Webmaster
CodeS-SourceS.com© est une marque déposée tous droits réservés
Temps d'éxécution de la page : 0,359 sec

Google Coop CodeS-SourceS Google Coop CodeS-SourceS


Certaines images présentes sur le site (notament certains avatars) sont issues des collections IconShock, donc si vous souhaitez utiliser ces icons vous devez les acheter, ne les copiez pas et ne utilisez pas dans vos sites et applications sans les avoir commandé.