问题描述
(只能使用.NET 3.5的股票,所以没有任务,没有任何反应扩展)
我有,我认为是一个简单的例子,但我在这百思不得其解。
它的短期是这样的,我回国BeginGetRequestStream的IAsyncResult的到BeginMyOperation()的调用者,我想真正发回BeginGetResponse的IAsyncResult的,当EndGetRequestStream被调用时调用。
所以,我想知道,我该怎么办
公众的IAsyncResult BeginMyOperation(...)
{
HttpWebRequest的WebRequest的=(HttpWebRequest的)WebRequest.Create(requestUri);
webRequest.Method =POST; //这是一部分,是困扰我。我不想这样的IAsyncResult送回去。
返回webRequest.BeginGetRequestStream(this.UploadingStreamCallback,状态);
} //只希望这个被称为当EndGetResponse已准备就绪。
公共无效EndMyOperation(IAsyncResult的AR)
{ } 私人IAsyncResult的UploadingStreamCallback(IAsyncResult的asyncResult)
{
使用(VAR S = state.WebRequest.EndGetRequestStream(asyncResult))
{
使用(VAR R =新BinaryReader(state.Request.RequestData))
{
字节[] = uploadBuffer新的字节[UploadBufferSize]
INT读取动作;
做
{
读取动作= r.Read(uploadBuffer,0,UploadBufferSize); 如果(读取动作大于0)
{
s.Write(uploadBuffer,0,读取动作);
}
}
而(读取动作大于0);
}
} //我真的想这样的IAsyncResult返回BeginMyOperation的调用者
返回state.WebRequest.BeginGetResponse(新的AsyncCallback(state.Callback),状态);
}
我觉得要解决这个最简单的方法是使用任务
包装。特别是,你可以完成一个。然后,只需返回。需要注意的是工作
工具的IAsyncResult
,让您的客户端code不会有改变。
就个人而言,我会走得更远了一步:
- 裹
BeginGetRequestStream
在工作
(使用的)。 - 创建为延续
工作
处理请求和包装BeginGetResponse
在任务
(再次使用FromAsync
)。 - 创建一个连续的第二个
即完成了
TaskCompletionSource
。 任务
恕我直言,异常和结果值更自然地工作
比的IAsyncResult
处理。
(can only use .NET 3.5 stock, so no Tasks, no Reactive Extensions)
I have, what I thought to be a simple case, but I'm baffled at it.
The short of it is that, I'm returning BeginGetRequestStream's IAsyncResult to the caller of BeginMyOperation(), and I want to really send back the IAsyncResult of BeginGetResponse, which is called when the EndGetRequestStream is called.
So I'm wondering, how do I
public IAsyncResult BeginMyOperation(...)
{
HttpWebRequest webRequest = (HttpWebRequest)WebRequest.Create(requestUri);
webRequest.Method = "POST";
// This is the part, that puzzles me. I don't want to send this IAsyncResult back.
return webRequest.BeginGetRequestStream(this.UploadingStreamCallback, state);
}
// Only want this to be called when the EndGetResponse is ready.
public void EndMyOperation(IAsyncResult ar)
{
}
private IAsyncResult UploadingStreamCallback(IAsyncResult asyncResult)
{
using (var s = state.WebRequest.EndGetRequestStream(asyncResult))
{
using (var r = new BinaryReader(state.Request.RequestData))
{
byte[] uploadBuffer = new byte[UploadBufferSize];
int bytesRead;
do
{
bytesRead = r.Read(uploadBuffer, 0, UploadBufferSize);
if (bytesRead > 0)
{
s.Write(uploadBuffer, 0, bytesRead);
}
}
while (bytesRead > 0);
}
}
// I really want to return this IAsyncResult to the caller of BeginMyOperation
return state.WebRequest.BeginGetResponse(new AsyncCallback(state.Callback), state);
}
I think the easiest way to solve this is to use Task
wrappers. In particular, you can finish a TaskCompletionSource
when BeginGetResponse
completes. Then just return the Task
for that TaskCompletionSource
. Note that Task
implements IAsyncResult
, so your client code won't have to change.
Personally, I would go a step further:
- Wrap
BeginGetRequestStream
in aTask
(usingFromAsync
). - Create a continuation for that
Task
that processes the request and wrapsBeginGetResponse
in aTask
(again, usingFromAsync
). - Create a continuation for that second
Task
that completes theTaskCompletionSource
.
IMHO, exceptions and result values are more naturally handled by Task
s than IAsyncResult
.
这篇关于等待是另一个等待的IAsyncResult一个IAsyncResult法(链接)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!