Comment lire (tampon, décalage, longueur) fonctionne réellement, si je passe la longueur à lire comme 32, cela signifie-t-il que cela continuerait à bloquer jusqu'à ce qu'il reçoive les 32 octets? P>
Je comprends que cela revenir et exception ou 0 en cas d'exception de socket ou si la connexion est fermée, respectivement. P>
Et si l'expéditeur envoie seulement 31 octets, lire continuer à bloquer? Si cela est vrai, cela signifie-t-il que la lecture renvoie toujours l'entier égal à la longueur qui lui est transmise? Et aussi comment CNAN je contrôle le délai d'attente si le 1 octet restant ne vient pas après un certain temps. P>
important et à ce jour non répondu à strong> p>
3 Réponses :
Non, il ne bloquera pas. L'opération de lecture lit autant de données que possible, jusqu'au nombre d'octets spécifiés par le paramètre Taille. Source: http://msdn.microsoft.com /en-us/library/system.net.sockets.networkstream.read.aspx
Étant donné que cela n'attendra pas cet octet supplémentaire, si vous l'attendez, vous devez implémenter une boucle pour continuer à lire le flux. Vous pouvez quitter la boucle, mais vous vous sentez le mieux. P>
mise à jour:
J'avais tort quand j'ai déclaré "il n'y a pas de blocage du tout. Si aucune donnée n'est disponible pour la lecture, la méthode de lecture renvoie 0", mais J'étais correct quand j'ai déclaré qu'il n'était pas bloqué pour remplir tout le tampon strong> que le scénario décrit dans la question de Kazoom. P> Mise à jour pour démontrer que NetworkStream.Read Blocks en attente du premier octet, mais Créer des projets de console P> sur une extrémité, vous avez l'écoute: p> sur l'autre extrémité, nous Envoyer un octet: p>
IPEndPoint ep = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 12345);
TcpClient client = new TcpClient();
client.Connect(ep);
client.GetStream().Write(new byte[] { 60 }, 0, 1);
Console.WriteLine("Press any key to continue...");
Console.Read();
donc il bloque au niveau des octets et pas de niveau de bit
Il n'y a pas de blocage du tout. Si aucune donnée n'est disponible pour la lecture, la méthode de lecture renvoie 0.
Qu'entendons-nous par aucune donnée disponible, que si l'expéditeur envoie 32 octets, cela garantit que la lecture ne reviendrait que après avoir lu ces 32 octets (en considérant qu'il s'agit d'une connexion TCP)
Vous êtes incorrect. Cela n'impose pas qu'il bloquera, mais il ressemblera à n'importe quel autre socket.
Je vais devoir trouver du code que j'ai écrit il y a quelques années. D'après ce que je me souviens que je devais mettre lu à l'intérieur d'une boucle parce qu'il y avait des circonstances quand je n'ai pas reçu tous les octets, je m'attendais à la fois. Je reviendrai vers toi.
@scottm: Vous devez mettre ce que je veux dire dans le contexte. Il va bloquer lors de la lecture du tampon sous-jacent. C'est pourquoi il y a une méthode appelée BeintureRead. Mais il ne bloquera pas l'attente de l'octet supplémentaire de 1 octet Kazoom indiqué dans son exemple. b>
@ Alfred, oui ça va. Essayez le code ASYNC que j'ai affiché, modifiez le tableau d'octets envoyé sur 31 au lieu de 32 et de la regarder.
@Scottm: Comme le démontre mon code, je m'attendais à recevoir 1, recevez 1 et il est retourné. Il ne bloque que lorsque rien n'est envoyé du tout, alors je suppose que nous étions tous les deux mal.
@Alfred, tu as raison. J'ai fait plus de recherche et j'ai mis à jour ma réponse. Cela a vraiment à voir avec la mise en œuvre du flux.Lead ().
Il bloquera jusqu'à ce qu'il reçoive 32 octets, ou la connexion est fermée. Les méthodes asynchrones BegneLead () et endread () doivent être utilisées pour fournir des lectures non bloquantes.
Voici quelques exemples de code démontrant clairement l'effet de blocage. p> Même si ce code produit la Effet de blocage, il est uniquement à cause de la mise en œuvre de Networkstream de Résumé de la diffusion Lecture () Méthode (qui doit être remplacée). La documentation sur flux.Read () indique ceci: P> Les implémentations renvoient le nombre de
octets lus. La valeur de retour est zéro
seulement si la position est actuellement à
la fin du flux. P>
blockQuote> C'est pourquoi le code bloque lorsque aucune donnée n'a été reçue et la fin du flux n'a pas été atteinte. Cela dit également: P> La mise en œuvre
MSDN.MicRosoft.com / FR-US / Bibliothèque / ...
Vous vous demandez simplement pourquoi la fonction doit renvoyer le nombre d'octets lu, mais il peut simplement renvoyer le statut de la lecture
@Kazoom, si vous lisez 20 octets et la connexion est fermée, le nombre renvoyé est 20.
La question est de savoir ce qui se passerait s'il recevait 31 octets lorsqu'il s'attendait à 32. Votre premier exemple est faux. Vous oublié B> d'accepter la connexion et vous oublié B> d'envoyer au moins un octet.
@Alfred, j'ai mis à jour ma réponse pour ajouter l'accepter là-bas. Il n'envoie toujours pas l'octet, mais cela explique dans mon édition.
La question sur le délai d'attente semblerait toujours être sans réponse. P>
La réponse est que vous pouvez définir stream.readtimeout et flux.writeTimeTout, où le flux est votre objet Networkstream. Cela gère le cas de blocage d'aucune réponse du tout. Sans définir ces valeurs, le flux attendra indéfiniment. P>
J'ai ajouté des échantillons de code démontrant que lire ne bloquera pas l'attente de remplir le tampon entier. Si vous n'envoyez rien, oui, il va bloquer, mais si vous envoyez au moins un octet, il lira et retournera.
Comment répondez-vous à la deuxième partie de la question, si j'envoie 32 octets et que je spécifie la longueur de 32 octets dans la méthode de lecture, cela garantit-il que ce serait certitude les 32 octets? Je veux dire qu'il bloquerait jusqu'à 32 octets.
@KAZOOM, je pense que cette question a déjà été répondue dans deux postes différents et leurs liens inclus. Il bloquera jusqu'à ce que au moins un octet soit reçu.