C # поток получил все данные? - PullRequest
11 голосов
/ 26 января 2009

Я использую C # .Net и класс Socket из пространства имен System.Net.Sockets. Я использую асинхронные методы получения. Я понимаю, что это легче сделать с помощью веб-службы; этот вопрос вызван моим любопытством, а не практической необходимостью.

Мой вопрос: предположим, что клиент отправляет какой-либо двоичный сериализованный объект неизвестной длины. На моем сервере с сокетом, как я знаю, что весь объект был получен и что он готов к десериализации? Я рассмотрел добавление объекта к длине объекта в байтах, но это кажется ненужным в мире .Net. Что происходит, если объект больше буфера? Откуда мне знать, «эй, нужно изменить размер буфера, потому что объект слишком большой»?

Ответы [ 3 ]

11 голосов
/ 26 января 2009

Вы либо хотите, чтобы протокол был самодействующим (как, например, XML, - вы знаете, когда вы закончили получать документ XML, когда он закрывает корневой элемент) или вам нужно задать префикс длины данных, или вам нужен другой конец, чтобы закрыть поток, когда это будет сделано.

В случае протокола с автоматическим завершением вам нужно иметь достаточно хуков, чтобы код чтения мог определить, когда он закончится. С двоичной сериализацией у вас может не хватить хуков. Префикс длины - безусловно, самое простое решение здесь.

4 голосов
/ 26 января 2009

Если вы используете чистые розетки, вам нужно знать длину. В противном случае размер буфера не имеет значения, потому что, даже если у вас есть буфер с размером целых данных, он все равно может не прочитать все в него - проверьте метод Stream.Read, он возвращает количество прочитанных битов, поэтому вам нужно выполнить цикл до получения всех данных.

0 голосов
/ 26 января 2009

Да, вы не сможете десериализовать, пока не получите все байты.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...