jjzjj

Javascript 生成器 : Understanding them

coder 2023-05-29 原文

我很确定我对生成器的理解天生就被打破了。所有在线资源似乎都相互冲突,这使得学习体验非常困难和困惑。

据我了解,yield 关键字使当前正在执行的代码块等待一个值,而不是在回调中抛出剩余的代码来执行。所以,正如大多数教程所指出的,你可以使用这个:

(function *() {
     // Wait until users have be got and put into value of `results`
     var results = yield db.get("users");
     // And continue
     view.display(results);
})();

代替:

db.get("user", function(results) {
    view.display(results);
});

好吧,在我尝试编写自己的生成器之前,一切都很好。我遇到了几个问题:

  • 我上面的第一个示例代码不会运行,因为没有什么可以迭代生成器,对吗?某些更高的存在必须在某处调用 .next,对吗?
  • 必须重写整个 API,直至 I/O 调用以支持生成器,对吗?
  • 据我所知,yield 似乎代表 等待值 最常见的用例,而在实现部分(阅读:返回值到/内部 db.get) yield 似乎代表将此值发送回当前等待的 block 以恢复执行

举个例子:

function *fn() {
    yield 1;
    yield "a";
}

var gen = fn();
gen.next(); // 1
gen.next(); // "a";

yield 在该上下文中是向下发送值而不是等待结果。在上面的第一个示例中,它等待来自 db.get 的结果并恢复执行,而不是“返回”或发回一个值。如果 db.get 情况为真,这不是天生同步的吗?我的意思是,它不完全一样:

(function() {
     //Wait for the results
    var results = fs.readFileSync("users.txt");
    // Use results
    view.display(results);
})();

不幸的是,如果从这个问题中可以清楚地看出(可能是唯一清楚的)就是我不了解生成器。希望我能在这里得到一些见解。

最佳答案

TL;DR:生成器的本质是控制代码执行的暂停。

生成器本身可以引用this .

总而言之,您应该区分三个组件: 1.生成器函数 2.发电机 3. 生成结果

Generator 函数只是一个 function,其头部带有星号,(可选)yield 在其主体中。

function *generator() {
  console.log('Start!');
  var i = 0;
  while (true) {
    if (i < 3)
      yield i++;
  }
}

var gen = generator();
// nothing happens here!!

Generator 函数本身只返回一个生成器,在上面的例子中,gen。 这里没有控制台输出,因为只有在返回的 generatornext 方法被调用后 generator function 的主体才会运行。 Generator 有几种方法,其中最重要的一种是nextnext 运行代码并返回生成器结果

var ret = gen.next();
// Start!
console.log(ret);
// {value: 0, done: false}

ret 上面是生成器结果。它有两个属性:value,你在generator function中产生的值,和done,一个标志generator function 返回。

console.log(gen.next());
// {value: 1, done: false}
console.log(gen.next());
// {value: 2, done: false}
console.log(gen.next());
// {value: undefined, done: true}

在这一点上,没有人会期望你了解生成器,至少不了解生成器的异步功能。

简单来说,生成器有两个特点:

  • 可以选择跳出函数,让外部代码决定何时跳回函数。
  • 异步调用的控制可以在您的代码之外完成

在代码中,yield 跳转到函数外,next(val) 跳转回函数并将值传回函数。 外部代码可以处理异步调用并决定适当的时间切换到您自己的代码。

再次查看示例:

var gen = generator();
console.log('generated generator');
console.log(gen.next().value);
// mock long long processing
setTimeout(function() {
  console.log(gen.next().value);
  console.log('Execute after timer fire');
}, 1000);
console.log('Execute after timer set');

/* result:
    generated generator
    start
    0
    Execute after timer set
    1
    Execute after timer fire
*/

看到了吗?生成器函数本身不处理回调。外部代码可以。

基地在这里。您可以详细说明此代码以支持完全异步,同时保持生成器功能类似于同步功能。

例如,假设 geturl 是一个异步调用,它返回一个 promise 对象。你可以写 var html = yield getUrl('www.stackoverflow.com'); 这会跳出你的代码。外部代码会执行以下操作:

var ret = gen.next();
ret.then(function (fetchedHTML) {
  // jumps back to your generator function
  // and assign fetchHTML to html in your code
  gen.next(fetchedHTML);
});

如需更完整的指南,请参阅 this . 以及像 co 这样的存储库, galaxy , suspend等等。

关于Javascript 生成器 : Understanding them,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/20768922/

有关Javascript 生成器 : Understanding them的更多相关文章

  1. ruby - 使用 RubyZip 生成 ZIP 文件时设置压缩级别 - 2

    我有一个Ruby程序,它使用rubyzip压缩XML文件的目录树。gem。我的问题是文件开始变得很重,我想提高压缩级别,因为压缩时间不是问题。我在rubyzipdocumentation中找不到一种为创建的ZIP文件指定压缩级别的方法。有人知道如何更改此设置吗?是否有另一个允许指定压缩级别的Ruby库? 最佳答案 这是我通过查看ruby​​zip内部创建的代码。level=Zlib::BEST_COMPRESSIONZip::ZipOutputStream.open(zip_file)do|zip|Dir.glob("**/*")d

  2. ruby - 在 jRuby 中使用 'fork' 生成进程的替代方案? - 2

    在MRIRuby中我可以这样做:deftransferinternal_server=self.init_serverpid=forkdointernal_server.runend#Maketheserverprocessrunindependently.Process.detach(pid)internal_client=self.init_client#Dootherstuffwithconnectingtointernal_server...internal_client.post('somedata')ensure#KillserverProcess.kill('KILL',

  3. ruby - 如何使用 Ruby aws/s3 Gem 生成安全 URL 以从 s3 下载文件 - 2

    我正在编写一个小脚本来定位aws存储桶中的特定文件,并创建一个临时验证的url以发送给同事。(理想情况下,这将创建类似于在控制台上右键单击存储桶中的文件并复制链接地址的结果)。我研究过回形针,它似乎不符合这个标准,但我可能只是不知道它的全部功能。我尝试了以下方法:defauthenticated_url(file_name,bucket)AWS::S3::S3Object.url_for(file_name,bucket,:secure=>true,:expires=>20*60)end产生这种类型的结果:...-1.amazonaws.com/file_path/file.zip.A

  4. ruby-on-rails - Ruby on Rails - 为文本区域和图片生成列 - 2

    我是Rails的新手,所以请原谅简单的问题。我正在为一家公司创建一个网站。那家公司想在网站上展示它的客户。我想让客户自己管理这个。我正在为“客户”生成一个表格,我想要的三列是:公司名称、公司描述和Logo。对于名称,我使用的是name:string但不确定如何在脚本/生成脚手架终端命令中最好地创建描述列(因为我打算将其设置为文本区域)和图片。我怀疑描述(我想成为一个文本区域)应该仍然是描述:字符串,然后以实际形式进行调整。不确定如何处理图片字段。那么……说来话长:我在脚手架命令中输入什么来生成描述和图片列? 最佳答案 对于“文本”数

  5. ruby-on-rails - 如何生成传递一些自定义参数的 `link_to` URL? - 2

    我正在使用RubyonRails3.0.9,我想生成一个传递一些自定义参数的link_toURL。也就是说,有一个articles_path(www.my_web_site_name.com/articles)我想生成如下内容:link_to'Samplelinktitle',...#HereIshouldimplementthecode#=>'http://www.my_web_site_name.com/articles?param1=value1¶m2=value2&...我如何编写link_to语句“alàRubyonRailsWay”以实现该目的?如果我想通过传递一些

  6. ruby-on-rails - 如何在 Rails 3 中创建自定义脚手架生成器? - 2

    有这些railscast。http://railscasts.com/episodes/218-making-generators-in-rails-3有了这个,你就会知道如何创建样式表和脚手架生成器。http://railscasts.com/episodes/216-generators-in-rails-3通过这个,您可以了解如何添加一些文件来修改脚手架View。我想把两者结合起来。我想创建一个生成器,它也可以创建脚手架View。有点像RyanBates漂亮的生成器或web_app_themegem(https://github.com/pilu/web-app-theme)。我

  7. 报告回顾丨模型进化狂飙,DetectGPT能否识别最新模型生成结果? - 2

    导读语言模型给我们的生产生活带来了极大便利,但同时不少人也利用他们从事作弊工作。如何规避这些难辨真伪的文字所产生的负面影响也成为一大难题。在3月9日智源Live第33期活动「DetectGPT:判断文本是否为机器生成的工具」中,主讲人Eric为我们讲解了DetectGPT工作背后的思路——一种基于概率曲率检测的用于检测模型生成文本的工具,它可以帮助我们更好地分辨文章的来源和可信度,对保护信息真实、防止欺诈等方面具有重要意义。本次报告主要围绕其功能,实现和效果等展开。(文末点击“阅读原文”,查看活动回放。)Ericmitchell斯坦福大学计算机系四年级博士生,由ChelseaFinn和Chri

  8. ruby-on-rails - 使用 javascript 更改数据方法不会更改 ajax 调用用户的什么方法? - 2

    我遇到了一个非常奇怪的问题,我很难解决。在我看来,我有一个与data-remote="true"和data-method="delete"的链接。当我单击该链接时,我可以看到对我的Rails服务器的DELETE请求。返回的JS代码会更改此链接的属性,其中包括href和data-method。再次单击此链接后,我的服务器收到了对新href的请求,但使用的是旧的data-method,即使我已将其从DELETE到POST(它仍然发送一个DELETE请求)。但是,如果我刷新页面,HTML与"new"HTML相同(随返回的JS发生变化),但它实际上发送了正确的请求类型。这就是这个问题令我困惑的

  9. python - 帮我找到合适的 ruby​​/python 解析器生成器 - 2

    我使用的第一个解析器生成器是Parse::RecDescent,它的指南/教程很棒,但它最有用的功能是它的调试工具,特别是tracing功能(通过将$RD_TRACE设置为1来激活)。我正在寻找可以帮助您调试其规则的解析器生成器。问题是,它必须用python或ruby​​编写,并且具有详细模式/跟踪模式或非常有用的调试技术。有人知道这样的解析器生成器吗?编辑:当我说调试时,我并不是指调试python或ruby​​。我指的是调试解析器生成器,查看它在每一步都在做什么,查看它正在读取的每个字符,它试图匹配的规则。希望你明白这一点。赏金编辑:要赢得赏金,请展示一个解析器生成器框架,并说明它的

  10. ruby - 如何为 pbcopy 生成富文本链接 - 2

    我一直在玩一个脚本,它在Chrome中获取选定的文本并在Google中查找它,提供四个最佳选择,然后粘贴相关链接。它以不同的格式粘贴,具体取决于当前在Chrome中打开的页面-DokuWiki打开的DokuWiki格式,普通网站的HTML,我想要我的WordPress所见即所得编辑器的富文本。我尝试使用pbpaste-Preferrtf来查看没有其他样式的富文本链接在粘贴板上的样子,但它仍然输出纯文本。在文本编辑中保存文件并进行试验后,我想出了以下内容text=%q|{\rtf1{\field{\*\fldinst{HYPERLINK"URL"}}{\fldrsltTEXT}}}|te

随机推荐