Чтение буфера из NetworkStream в асинхронном обратном вызове - PullRequest
1 голос
/ 05 апреля 2019

См. Также Понимание примера NetworkStream.EndRead () из MSDN .

Я пытаюсь выполнить асинхронное чтение из NetworkStream с использованием методов BeginRead и EndRead (в частности, я хочу открыть NetworkStream, выполнить различные другие задачи, а затем обработать данные, полученные наNetworkStream).Пример MSDN для EndRead ( здесь ) имеет различные проблемы и не работает как есть, как отмечено в связанном вопросе.Ответ на этот вопрос показывает, как должен быть структурирован базовый код, но он не включает фактическое чтение данных из NetworkStream в обратном вызове.

В функции обратного вызова, как мне передать данныекоторый был прочитан из NetworkStream в буфер?

EDIT

Это оригинальный пример MSDN.

public static void myReadCallBack(IAsyncResult ar )
{
    NetworkStream myNetworkStream = (NetworkStream)ar.AsyncState;
    byte[] myReadBuffer = new byte[1024];
    String myCompleteMessage = "";
    int numberOfBytesRead;

    numberOfBytesRead = myNetworkStream.EndRead(ar);
    myCompleteMessage = String.Concat(myCompleteMessage,Encoding.ASCII.GetString(myReadBuffer, 0, numberOfBytesRead));    

    // message received may be larger than buffer size so loop through until you have it all.
    while(myNetworkStream.DataAvailable)
    {
        myNetworkStream.BeginRead(myReadBuffer, 0, myReadBuffer.Length, new AsyncCallback(NetworkStream_ASync_Send_Receive.myReadCallBack), myNetworkStream);  
    }

    // Print out the received message to the console.
    Console.WriteLine("You received the following message : " + myCompleteMessage);
}

Основная проблема с этимНапример, данные не передаются из NetworkStream в myReadBuffer.

EDIT 1

Благодаря Дмитрию Мукалову работает следующий код:

internal class CallbackArgs
{
    public NetworkStream Stream { get; set; }
    public byte[] Buffer { get; set; }

    public CallbackArgs(NetworkStream stream, byte[] buffer)
    {
        Stream = stream;
        Buffer = buffer;
    }
}

//  In the caller:

    //  (Create and open thisNetworkStream, and check thisNetworkStream.CanRead)

    byte[] thisReadBuffer = new byte[1024];
    CallbackArgs args = new CallbackArgs(thisNetworkStream, thisReadBuffer);
    thisNetworkStream.BeginRead(thisReadBuffer, 0, thisReadBuffer.Length, new AsyncCallback(myReadCallBack), args);

//  The callback function:
public static void myReadCallBack(IAsyncResult ar)
{
    CallbackArgs args = (CallbackArgs)ar.AsyncState;
    NetworkStream myNetworkStream = args.Stream;
    byte[] myReadBuffer = args.Buffer;

    //  myReadBuffer now contains the data read from the network stream.

    int bytesRead = myNetworkStream.EndRead(ar);

    //  Do work on myReadBuffer, etc.
}

1 Ответ

1 голос
/ 05 апреля 2019

Когда выполняется обратный вызов, данные уже передаются в буфер, переданный на предыдущий вызов BeginRead.Проблема с данным примером в том, что он пытается использовать локальный буфер myReadBuffer для чтения исходного сообщения.Вместо этого вы должны сделать буфер, переданный в BeginRead доступным для EndRead.Вы можете сделать это, сделав его экземпляром члена класса для этого буфера, передав его вместе с NetworkStream как state аргумент BeginRead, используя переменную закрытия в некотором методе, который будет инициировать цикл чтения и т. Д.

...