C#:阻塞函数调用,直到满足条件
我正在开发一个 C# Winforms 应用程序,该应用程序的一部分将使用 AsyncUpload 将文件上传到网络服务器(使用它,因为需要使用 porgress 回调),在 C# 程序中,
我有一个简单的 for 循环,它调用上传function
for(int i=0;i < 10 ; i++)
{
Uploadfun();
}
并且 fun 做了一些魔力:
Uploadfun()
{
// Logic comes here
// webClient.UploadFileAsync runs a 2nd thread to perform upload ..
webClient.UploadFileAsync(uri, "PUT", fileNameOnHD);
}
异步上传完成时调用的回调
Upload_Completed_callback()
{
//Callback event
}
编辑
逻辑顺序:
- Fun 被调用(从循环)
- Fun 逻辑被执行并完成..
- 返回for循环
- 回调最终将被调用,当UploadFileAsync(正在另一个线程中运行一些逻辑)结束时
问题是在第三点上,当执行移回for循环时,我需要阻止循环继续,直到回调被调用。
I am developing a C# Winforms application, part of the application will be uploading files to a webserver using AsyncUpload (using it,due to the need to use a porgress callback) , In the C# program
i got a simple for loop that calls The Uploading function
for(int i=0;i < 10 ; i++)
{
Uploadfun();
}
And the fun does some magic:
Uploadfun()
{
// Logic comes here
// webClient.UploadFileAsync runs a 2nd thread to perform upload ..
webClient.UploadFileAsync(uri, "PUT", fileNameOnHD);
}
And a callback that gets called when the Async upload is done
Upload_Completed_callback()
{
//Callback event
}
Edit
The logic sequence:
- Fun gets called (from loop)
- Fun logic is executed and done..
- Goes back to for loop
- Callback will be called eventually, when UploadFileAsync (which is running some logic in another thread) will end
The problem is on the 3rd point, when the execution moves back to the for loop, i need to block the loop from continuing until the callback get called.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
因此,如果我理解正确,您需要调用
UploadFileAsync
然后阻塞,直到异步调用命中您的回调。如果是这样,我会使用 AutoResetEvent 即使用 AutoResetEvent 意味着在调用 Set 后状态会自动重置并且等待线程接收到通过
WaitOne
发出信号So if I understand correctly, you want to call
UploadFileAsync
then block until the async call has hit your callback. If so, I'd useAutoResetEvent
i.eUsing
AutoResetEvent
means that the state gets automatically reset afterSet
has been called and a waiting thread receives the signal viaWaitOne
在 C# 方法中,默认情况下会阻塞,因此您不需要执行任何操作。我假设由于某种原因您正在调用一个非阻塞方法来启动后台任务/线程/无论什么,并在完成时给您一个回调。您希望以同步方式调用此异步方法。
您可以从回调内部调用
fun
。类似的东西(伪代码):这类似于连续传递样式。
此方法的一个优点是,您还可以使方法异步,而无需添加任何额外的线程、锁或额外的逻辑 - 您只需提供客户端可以订阅的回调函数。它在事件驱动的环境中运行良好。
In C# methods block by default, so you shouldn't need to do anything. I'm assuming that for some reason you are calling a non-blocking method that starts a background task / thread / whatever and gives you a callback when it's done. You want to call this asynchonous method in a synchronous manner.
You can call
fun
from inside the callback. Something along these lines (pseudo-code):This is similar to continuation passing style.
An advantage to this method is that you can also make your method asynchronous without adding any extra threads, locks, or extra logic - you just supply a callback function which your client can subscribe to. It works well in an event-driven environment.
Zebrabox 确实正确地使用了 WaitHandle。
虽然 Juliet 的解决方案确实有效,但执行自旋等待的线程将消耗与 WaitHandle 成比例的大量处理器,而 WaitHandle 基本上处于空闲状态。
Zebrabox does have it right using a WaitHandle.
While Juliet's solution does work, the thread performing the spin-wait will consume a significant amount of processor in proportion to the WaitHandle, which would essentially be sitting idle.
问题就在这里:
你正在做的事情是连续的。如果您无法阻止 UI 线程,请将循环移出 UI 线程:
现在您可以在不停止 UI 线程的情况下阻止循环的执行,并且您还可以从 Webclient 类中获得进度指示器的好处。
The problem is here:
What you're doing is sequential. And if you can't afford to block the UI thread, move the loop off the UI thread:
Now you can block the execution of the loop without halting your UI thread, and you also get the benefit of progress indicators from the webclient class.