首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >C#“事件循环”与JavaScript“事件循环”相比如何?

C#“事件循环”与JavaScript“事件循环”相比如何?
EN

Stack Overflow用户
提问于 2016-01-10 20:36:06
回答 2查看 7.2K关注 0票数 3

我理解JavaScript事件循环的地方是当我听到它被描述为

“当没有事可做时,检查队列,但只有在没有事情可做的时候才检查队列。”

在视频https://www.youtube.com/watch?v=vMfg0xGjcOI中。

例如,如果我的JS程序的全部内容是

代码语言:javascript
复制
var x = 5.0;  
setTimeout(0,function(){console.log("Hey there!");});
for ( var i = 0; i < 10000; ++i ) x = Math.sqrt(x);
console.log("x = " + x);

然后将回调function(){console.log("Hey there!");}放在队列中,因此将在console.log("x = " + x);之后执行,因为此时没有什么可做的了。

在C#中,正如我所理解的--我并不真正理解--事情是不同的,因为“回调”的等价物并不是等待没有什么可做的,而是中断了另一个进程(Es)。这就是我对

在写入请求开始后的一段时间内,设备将完成写入。它通过中断通知CPU。 设备驱动程序的中断服务例程(ISR)响应中断。中断是CPU级别的事件,暂时从运行的线程中获取CPU的控制权。你可以把ISR看作是“借用”当前运行的线程,但我更倾向于认为ISRs在如此低的层次上执行,以至于“线程”的概念根本不存在--因此,可以说,它们“在所有线程之下”出现。 无论如何,ISR是正确编写的,所以它所做的就是告诉设备“感谢您的中断”,并排队一个延迟过程调用(DPC)。 当CPU被中断所困扰时,它会转移到它的DPC上。DPC的执行级别也非常低,以至于谈论“线程”并不完全正确;与ISRs一样,DPC直接在CPU上执行,“在线程系统下”执行。

来自http://blog.stephencleary.com/2013/11/there-is-no-thread.html。所以如果我写了相当于

代码语言:javascript
复制
var x = 5.0;  
setTimeout(0,function(){console.log("Hey there!");});
for ( var i = 0; i < 10000; ++i ) x = Math.sqrt(x);
console.log("x = " + x);

在C#中,这将类似于

代码语言:javascript
复制
var x = 5.0;  
await SomeAsynchronousRoutine();
for ( var i = 0; i < 10000; ++i ) x = Math.Sqrt(x);
Console.WriteLine("x = {0}",x);   

实际上,循环for ( var i = 0; i < 10000; ++i )可能被中断以传递SomeAsynchronousRoutine()的结果。

还是我完全错了,应该为没有做足够的研究而问一个问题而感到羞愧?

如果您必须用如下的方式来描述C#“事件循环”

“当没有事可做时,检查队列,但只有在没有事情可做的时候才检查队列。”

那你会怎么形容呢?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2016-01-10 21:05:29

因为c#是多线程和JavaScript is single threaded。我会说它有点不同。

等待指令意味着,您提供的特定的六行代码将在异步例程完成之前,不会继续执行

但是,这并不意味着所有其他代码都会挂起。当这个特定的例程冷却时,您的主线程可以自由地运行其他代码。

考虑一下jquery动画。当你运行一些冗长的、过于复杂的代码时,它们就会停止,对吗?c# ui就不是这样了。如果在anync任务中抛出长卷的代码并正确地启动它,您的ui动画代码就可以不闪烁地运行。

更好的是--我可以启动一堆异步任务(每个任务都是冗长而繁琐的),它们都(在自己的线程中)做自己的事情,而不互相打扰(或者冻结我的ui,或者垄断iis请求线程等等)。

你上面引用的一点“智慧”是在谈论一个更深层次的问题。它的意思是“如果您有回调(而不是等待),cpu如何管理中断?”

我无法想象有人会关心这个问题的答案,但也许我已经明白了你问错了什么。对不起,如果是这样的话!

希望这能帮上忙。

票数 5
EN

Stack Overflow用户

发布于 2018-08-31 04:46:10

您混淆了c#中的javascript回调和等待操作符,它们是不一样的。回调将与Action中的c#相同。

你的例子全错了。

代码语言:javascript
复制
var x = 5.0;
setTimeout(0,function(){console.log("Hey there!");});
for ( var i = 0; i < 10000; ++i ) x = Math.sqrt(x);
console.log("x = " + x);
代码语言:javascript
复制
var x = 5.0;
await SomeAsynchronousRoutine();
for ( var i = 0; i < 10000; ++i ) x = Math.Sqrt(x);
Console.WriteLine("x = {0}",x);

你需要这样做

代码语言:javascript
复制
var x = 5.0;
Task.Run(() => {
   Console.WriteLine("Hey there!");
});
for ( var i = 0; i < 10000; ++i ) x = Math.Sqrt(x);
Console.WriteLine("x = {0}",x);

现在,C#被多线程化的好处是,每当任务调度程序接近它时,我的回调(Action)就会被执行,可能在循环中的任何一点。

现在假设我想要一个线程所经历的相同的行为,您需要做如下所示的事情

代码语言:javascript
复制
var x = 5.0;
var lck = new SemaphoreSlim(1);
Task.Run(async () => {
   await lck.WaitAsync();
   Console.WriteLine("Hey there!");
});
for ( var i = 0; i < 10000; ++i ) x = Math.Sqrt(x);
Console.WriteLine("x = {0}",x);
lck.Release();

不要担心,多线程环境中的异步编程是很难掌握的。其中的原因之一,我真的喜欢高丽(chans,范围和选择?哦,天哪!)

学习SemaphoreSlim!你可以做各种各样的调用,比如创建一个AsyncQ!

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/34710487

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档