- c - 在位数组中找到第一个零
- linux - Unix 显示有关匹配两种模式之一的文件的信息
- 正则表达式替换多个文件
- linux - 隐藏来自 xtrace 的命令
我读了this article关于 Task.ConfigureAwait
,它有助于防止异步代码中的死锁。
看看这段代码:(我知道我不应该做 .Result
,但这是问题的一部分)
private void Button_Click(object sender, RoutedEventArgs e)
{
string result = GetPageStatus().Result;
Textbox.Text = result;
}
public async Task<string> GetPageStatus()
{
using (var httpClient = new HttpClient())
{
var response = await httpClient.GetAsync("http://www.google.com");
return response.StatusCode.ToString();
}
}
这将导致死锁,因为:
.Result
- 操作将在等待异步操作完成时阻塞当前线程(即 UI 线程)。
网络调用完成后,它将尝试继续执行 response.StatusCode.ToString()
- 在捕获的上下文中的方法。 (被阻止 - 因此出现死锁)。
一个解决方案是使用:
var response = await httpClient.GetAsync("http://www.google.com").ConfigureAwait(false);
但其他解决方案是一直异步(不阻塞):
/*1*/ private async void Button_Click(object sender, RoutedEventArgs e)
/*2*/ {
/*3*/ string result = await GetPageStatus();
/*4*/ Textbox.Text = result;
/*5*/ }
/*6*/ public async Task<string> GetPageStatus()
/*7*/ {
/*8*/ using (var httpClient = new HttpClient())
/*9*/ {
/*10*/ var response = await httpClient.GetAsync("http://www.google.com");
/*11*/ return response.StatusCode.ToString();
/*12*/ }
/*13*/ }
问题:
(我试图了解这段代码如何帮助解决问题 - 通过上下文 POV)。
#3
行和 #10
行是否捕获了不同的上下文?
我认为的流动方式是否正确:
第 3 行调用了第 6 行(后者调用了第 10 行),发现它尚未完成,因此它等待(#3 的捕获上下文 = UI 线程)。
稍后,第 10 行捕获另一个上下文(我将其称为 newContext)完成后,它返回到“newContext”,然后释放 UI 上下文(线程)。
我说的对吗?
最佳答案
Does line #3 and line #10 captures different contexts ?
从您的代码来看,没有。它们都将捕获相同的 UI 同步上下文,因为您不使用 ConfigureAwait(false)
这会阻止将延续编码回 UI 上下文。
Am I right regarding the way of flow as I think it is :
line #3 calls #6 (which calls #10) and sees that it didnt finish yet , so it awaits ( captured context for #3= UI thread).
Later on , line #10 capture another context ( I will call it newContext) after it finishes , it is back to "newContext" and then releases the UI context(thread).
差不多。您的通话中没有创建“新上下文”。它始终是相同的 UI 同步上下文。例如,如果您有两个异步调用一个接一个,当一个调用使用 ConfigureAwait(false)
时,第二个调用将继续在线程池线程上执行。
至于您的可视化,它确实正确地捕获了代码的执行流程。
关于c# - 等待和预防死锁 - 澄清?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27636869/
我有类似下面的代码: ... id: myComponent signal updateState() property variant modelList: [] Repeater { mo
我正在处理一些我无法展示的私有(private)代码,但我已经制作了一些示例代码来描述我的问题: 主.c: #include #include #include #include typede
这个问题在这里已经有了答案: 关闭10 年前。 Possible Duplicate: what are the differences in die() and exit() in PHP? 我想
在编写 Perl 模块时,在模块内部使用 croak/die 是一个好习惯吗? 毕竟,如果调用者不使用 eval block ,模块可能会使调用它的程序崩溃。 在这些情况下,最佳做法是什么? 最佳答案
我有一些搜索线程正在存储结果。我知道当线程启动时,JVM native 代码会代理在操作系统上创建新 native 线程的请求。这需要 JVM 之外的一些内存。当线程终止并且我保留对它的引用并将其用作
我刚刚花了很多时间调试一个我追溯到 wantarray() 的问题。 .我已将其提炼为这个测试用例。 (忽略 $! 在这种情况下不会有任何有用信息的事实)。我想知道为什么wantarray在第二个示例
我看到一些代码是这样做的: if(something){ echo 'exit from program'; die; } ...more code 和其他只使用 die 的人: if
我正在尝试将此表格用于: 如果任何 $_POST 变量等于任何其他 $_POST 变量抛出错误。 如果只有几个,那不是问题,但我有大约 20 个左右所以如果我想这样做,我将不得不像这样 但这
每次我运行: hadoop dfsadmin -report 我得到以下输出: Configured Capacity: 0 (0 KB) Present Capacity: 0 (0 KB) DFS
我是一名优秀的程序员,十分优秀!