首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

为什么我的递归函数在循环中涉及异步调用,而不返回到调用者函数来继续循环?

在涉及异步调用的循环中,递归函数不返回到调用者函数来继续循环的原因有几个方面:

  1. 异步调用的特性:异步调用是一种非阻塞的方式,它会将任务交给其他线程或进程去执行,并立即返回到调用者函数,而不会等待任务完成。这种机制使得递归函数无法像同步调用那样在循环中继续执行。
  2. 避免阻塞主线程:在循环中涉及异步调用时,如果递归函数阻塞主线程来等待异步任务完成,会导致整个应用程序的响应性下降,用户体验差。因此,为了避免阻塞主线程,递归函数不会返回到调用者函数,而是将异步任务的处理交给其他线程或进程来执行。
  3. 异步任务的结果处理:在循环中涉及异步调用时,递归函数通常会通过回调函数或Promise等方式来处理异步任务的结果。这意味着递归函数会在异步任务完成后被调用,而不是在循环中继续执行。

总的来说,递归函数在循环中涉及异步调用时,不返回到调用者函数来继续循环是为了遵循异步调用的特性,避免阻塞主线程,并通过回调函数或Promise等方式处理异步任务的结果。这样可以提高应用程序的响应性和用户体验。

页面内容是否对你有帮助?
有帮助
没帮助

相关·内容

Go的面试笔试基础考察区别点

面试: 1)go写的递归函数调用栈会溢出吗?: 大部分编程语言使用固定大小的函数调用栈,常见的大小从64KB到2MB不等。...这使得我们使用递归时不必考虑溢出 和安全问题 2) 函 数值可以比较么? // squares返回一个匿名函数。 // 该匿名函数每次被调用时都会返回下一个数的平方。...对squares的一次调用会生成一个局部变量x并返 回一个匿名函数。 每次调用时匿名函数时,该函数都会先使x的值加1,再返回x的平方。...在squares中定义的匿名内部函数 可以访问和更新squares中的局部变量,这意味着匿名函数和squares中,存在变量引用。 这就是函 数值属于引用类型和函数值不可比较的原因。...在上面的程序中,for循环语句引入了新的词法块,循环变量 dir在这个词法块中被声明。在该循环中生成的所有函数值都共享相同的循环变量。

1.6K20

异步,同步,阻塞,非阻塞程序的实现

什么是异步,同步,阻塞,非阻塞 在写这篇文章前,我对这四个概念是非常模糊的。 同步,异步 异步同步的差异,在于当线程调用函数的时候,线程获取消息的方式....如果是同步,线程会等待接受函数的返回值(或者轮循函数结果,直到查出它的返回状态和返回值)。如果是异步,线程不需要做任何处理,在函数执行完毕后会推送通知或者调用回调函数。...同步: 线程 ----我主动来拿结果----> 函数 异步: 线程 函数 阻塞,非阻塞 阻塞非阻塞的差异,在于线程调用函数的时候,线程的状态。...线程在同步调用下,也能非阻塞(同步轮循非阻塞函数的状态),在异步下,也能阻塞(调用一个阻塞函数,然后在函数中调用回调,虽然没有什么意义)。 下面,我会慢慢实现一个异步非阻塞的sleep。...上面的代码中,在一个while循环中轮循timer的状态。由于timer存在于wait中。所以需要把timer“提取”出来。

7.6K10
  • 阻塞与非阻塞的区别verilog_如何理解阻塞和非阻塞

    简单点说: 阻塞就是干不完不准回来, 非阻塞就是你先干,我现看看有其他事没有,完了告诉我一声 我们拿最常用的send和recv两个函数来说吧… 比如你调用send函数发送一定的Byte,在系统内部...该函数发送一个消息给某个窗口,在对方处理完消息之前,这个函数不返回。当对方处理完毕以后,该函数才把消息处理函数所返回的 LRESULT值返回给调用者。 异步 异步的概念和同步相对。...当一个异步过程调用发出后,调用者不能立刻得到结果。实际处理这个调用的部件在完成后,通过状态、通知和回调来通知调用者。...如果执行部件用状态来通知,那么调用者就需要每隔一定时间检查一次,效率就很低(有些初学多线程编程的人,总喜欢用一个循 环去检查某个变量的值,这其实是一种很严重的错误)。...例如,我们在CSocket中调用Receive函数,如果缓冲区中没有数据,这个函数就会一直等待,直到有数据才返回。而此时,当前线程还会继续处理各种各样的消息。

    2.3K20

    【STM32F429】第7章 RTX5任务管理

    应用程序是一个无限的循环,循环中调用相应的函数完成相应的操作,这部分可以看做后台行为,中断服务程序处理异步事件,这部分可以看做是前台行为。后台也可以叫做任务级,前台也叫作中断级。...(3) 低优先级任务执行的过程中产生USB中断,进入USB中断服务程序。 (4) 退出USB中断复位程序,回到低优先级任务继续执行。...一旦进入了中断函数已经可能发生的中断嵌套都是用的MSP指针。这个知识点要记住他,当前可以不知道这是为什么,但是一定要记住。...函数参数: 返回值: osError 表示未指定类型的错误。 osErrorISR 表示不支持在中断服务程序里面调用。 注意事项: 这个函数不可以在中断服务程序里面调用。...注意事项: 这个函数不可以在中断服务程序里面调用。 此函数可以在osKernelStart前调用,但不可以在osKernelInitialize前调用。

    61820

    【STM32H7】第7章 RTX5任务管理

    应用程序是一个无限的循环,循环中调用相应的函数完成相应的操作,这部分可以看做后台行为,中断服务程序处理异步事件,这部分可以看做是前台行为。后台也可以叫做任务级,前台也叫作中断级。...(3) 低优先级任务执行的过程中产生USB中断,进入USB中断服务程序。 (4) 退出USB中断复位程序,回到低优先级任务继续执行。...一旦进入了中断函数已经可能发生的中断嵌套都是用的MSP指针。这个知识点要记住他,当前可以不知道这是为什么,但是一定要记住。...函数参数: 返回值: osError 表示未指定类型的错误。 osErrorISR 表示不支持在中断服务程序里面调用。 注意事项: 这个函数不可以在中断服务程序里面调用。...注意事项: 这个函数不可以在中断服务程序里面调用。 此函数可以在osKernelStart前调用,但不可以在osKernelInitialize前调用。

    70530

    【STM32F407】第7章 RTX5任务管理

    应用程序是一个无限的循环,循环中调用相应的函数完成相应的操作,这部分可以看做后台行为,中断服务程序处理异步事件,这部分可以看做是前台行为。后台也可以叫做任务级,前台也叫作中断级。...(3) 低优先级任务执行的过程中产生USB中断,进入USB中断服务程序。 (4) 退出USB中断复位程序,回到低优先级任务继续执行。...一旦进入了中断函数已经可能发生的中断嵌套都是用的MSP指针。这个知识点要记住他,当前可以不知道这是为什么,但是一定要记住。...函数参数: 返回值: osError 表示未指定类型的错误。 osErrorISR 表示不支持在中断服务程序里面调用。 注意事项: 这个函数不可以在中断服务程序里面调用。...注意事项: 这个函数不可以在中断服务程序里面调用。 此函数可以在osKernelStart前调用,但不可以在osKernelInitialize前调用。

    63030

    JAVA高性能IO设计模式

    通过AsynchronousServerSocketChannel中注册事件回调函数来处理业务逻辑。当IO操作完成以后,回调函数会被调用。...,当IO事件分发器会通知可读写时再继续进行读写,不断循环直到读写完成)  系统I/O 可分为阻塞型, 非阻塞同步型以及非阻塞异步型。...阻塞型I/O意味着控制权只到调用操作结束了才会回到调用者手里。 结果调用者被阻塞了, 这段时间了做不了任何其它事情。...调用函数在立即返回时,还告诉调用者,这次请求已经开始了。系统会使用另外的资源或者线程来完成这次调用操作,并在完成的时候知会调用者(比如通过回调函数)。...主动和被动 Reactor模式是一种被动的处理,即有事件发生时被动处理。而Proator模式则是主动发起异步调用,然后循环检测完成事件。

    89120

    ES6中的尾调用优化

    粗略的来说,如果当一个函数所做的最后一件事是调用了另一个函数,而后者不需要向调用者返回任何东西时;以及由此可知,在这种情况下没有调用者的额外信息需要被储存在调用栈(call stack)上,函数间的调用更像一种...在行B中,从id中返回的值将继续返回给f的调用者。照旧,最上面的调用帧被移除,执行过程跳转到要return的位置 -- 行C。 ? Step 6. 行C接收到返回值3并完成打印工作。...id()返回了数值3,或者可以说它为f()返回了这个值;因为通过行C,该值被传递给了f的调用者。 不难发现,行B的函数调用就是一个尾调用。这样的调用可以在栈0增长的情况下完成。...尾递归函数 如果一个函数的主递归调用发生在尾部,那这个函数就是尾递归。...3.1 尾递归循环 尾调用优化使得在递归循环中不增长调用栈成为可能。下面举两个例子。

    94720

    生生世世 —— schedule 的轮回(七)

    schedule 函数开始,经过一系列过程再次调用 schedule 函数来进行新一轮的调度,从一轮调度到新一轮调度的过程称之为一个调度循环。...从前面的代码分析可以得知,上面调度循环中的每一个函数调用都没有返回,虽然 goroutine任务->goexit()->goexit1()->mcall() 是在 g2 的栈空间执行的,但剩下的函数都是在...那么问题就来了,在一个复杂的程序中,调度可能会进行无数次循环,也就是说会进行无数次没有返回的函数调用,大家都知道,每调用一次函数都会消耗一定的栈空间,而如果一直这样无返回的调用下去无论 g0 有多少栈空间终究是会耗尽的...我再解释一下:栈空间在调用函数时会自动“增大”,而函数返回时,会自动“减小”,这里的增大和减小是指栈顶指针 SP 的变化。...上述这些函数都没有返回,说明调用者不需要用到被调用者的返回值,有点像“尾递归”。 因为 g0 一直没有动过,所有它之前保存的 sp 还能继续使用。每一次调度循环都会覆盖上一次调度循环的栈数据,完美!

    56920

    c#异步编程-Task(二)

    一、概要 大家好,本次继续分享自己的学习经历。本文主要分享Task异步编程内容,如果能帮助大家希望多多关注文章末尾的微信公众号和知乎三连。各位举手之劳是对我更新技术文章最大的支持。...把task返回调用者,创建异步方法; 异步编程的区别:目标是在调用图较低的位置来这样做。...; } 当点击按钮,event handler运行时,在await后,执行会正常的返回到消息循环1秒钟之后抛出的异常无法被消息循环中的catch块捕获。...不直接将异常抛出回调用者的原因是为了确保可预测性和一致性。...Task,就可以避免此类错误的发生: Task valueTask = Foo().AsTask(); 避免过度的弹回 对于在循环中多次调用的方法,通过调用ConfigureAwait方法,就可以避免重复的弹回到

    2.6K30

    详解 JS 中的事件循环、宏微任务、Primise对象、定时器函数,以及其在工作中的应用和注意事项

    为什么会然想到写这么一个大杂烩的博文呢,必须要从笔者几年前的一次面试说起 当时的我年轻气盛,在简历上放了自己的博客地址,而面试官应该是翻了我的博客,好几道面试题都是围绕着我的博文来提问 其中一个问题,直接使得空气静止了五分钟...什么是宏任务(MacroTasks)和 微任务(MicroTasks) 宏任务 宏任务是 JavaScript 事件循环中的一个较大的任务单元,每个宏任务在执行时会开启一个新的事件循环 一个宏任务的完成通常会涉及到一个较为完整的工作流程...内存泄漏:在某些情况下,定时器的回调函数可能引用了外部变量或者大型数据结构,如果定时器没有被销毁,这些引用关系可能导致所涉及的内存无法被垃圾回收,从而造成内存泄漏。...process.nextTick 在工作中应用的注意事项 递归调用:如果 process.nextTick 被递归调用,或在一个循环中大量调用,它可以导致I/O饿死,因为它会在处理任何I/O事件之前不断地将新的回调加入到队列中...为什么要销毁定时器? 我是 fx67ll.com,如果您发现本文有什么错误,欢迎在评论区讨论指正,感谢您的阅读!

    29610

    【面试宝典】深入Python高级:直戳痛点的题目演示(上)

    列表的反转:reversed 函数、sorted函数、切⽚技术、循环,递归,四种⽅式 字典的反转:循环,推导式,压缩器三种⽅式 列表反转: 字典反转: 装饰器是什么,什么场景⽤到装饰器,举个例...my_iterator ,然后使⽤ while 循 环和 next() 函数来依次访问迭代器中的元素。...⽣成器(Generator)是⼀种特殊的迭代器,它使⽤⽣成器函数来⽣成序列中的元素,⽽不 是在内存中⼀次性⽣成所有元素。...在函数中,我们使⽤ yield 语句返回斐波那契数列中的每⼀个元素,这样每次调⽤ next() 函数时,它会返回下⼀个元素,并在下次调⽤时从上次暂停的位置继续执⾏。...或者说为什么装饰器要写2层嵌套函数,⾥层函数完全就已经实现了装饰的功能为什么不直接⽤⾥层函数名作为装饰器名称?

    10310

    UE4UE5的TaskGraph

    在Windows上封装的Event内核对象,Wait实际是调用WaitForSingleObject来阻塞,而Trigger是调用SetEvent来唤醒的。...- 知乎 (zhihu.com) TaskGraph 异步Task 要执行异步Task,最简单的就是使用Async这个全局函数: 可以看到,其实这个函数就是一个通用的执行异步逻辑的函数,异步的Task...当一个Task进来时,如果指定了线程就直接丢入对应线程的消息队列,命名线程会在一个大循环中持续取Task来执行。...AnyThread的模式 ProcessTasksUntilQuit 持续执行Task,如果没Task了也继续循环取,根据参数决定是否Stall(渲染线程会Stall) 必须主动调用...而对于一开始不想马上执行的Task,UE也提供了一个Hold函数,其实本质就是让计数设为1,当主动调用Unlock时,才会把Task解锁继续执行。

    5.8K31

    C#-筆記-基礎

    break 语句不能用于循环语句和 switch 语句之外的任何其他语句中。 continue 语句只结束本次循环,而不是终止整个循环。...同理反之:int min = int.MinValue; 方法 我們在main函數中,調用Test()函數(方法),我們管main()函數稱之為調用者,管Test函數是被調用者。...意思是將你提供的一係類數據當做一個數組計算。當然了這個數組是不可以變化的。 這是我自己說的不知道對不對。 方法的重載 定義:就是方法的名稱相同方法的參數不同。...2.如果類型相同參數的個數就不能相同。 方法的重載和返回值沒有關係。 递归 递归分为两种,直接递归和间接递归。 直接递归称为方法自身调用自己。...间接递归可以A方法调用B方法,B方法调用C方法,C方法调用A方法。 注意事项: 递归一定要有条件限定,保证递归能够停止下来,否则会发生栈内存溢出。 在递归中虽然有限定条件,但是递归次数不能太多。

    48630

    在chromev8中的JavaScript事件循环分析

    每一个消息都关联着一个用以处理这个消息的回调函数。 在事件循环期间的某个时刻,运行时会从最先进入队列的消息开始处理队列中的消息。被处理的消息会被移出队列,并作为输入参数来调用与之关联的函数。...而当一系列方法被依次调用的时候,因为js是单线程的,同一时间只能执行一个方法,于是这些方法被排队在一个单独的地方。这个地方被称为执行栈。...在事件循环中,每进行一次循环操作称为tick,每一次tick的任务处理模型是比较复杂的,但关键步骤如下: 执行一个宏任务(栈中没有就从事件队列中获取) 执行过程中如果遇到微任务,就将它添加到微任务的任务队列中...: 执行宏任务,然后执行该宏任务产生的微任务,若微任务在执行过程中产生了新的微任务,则继续执行微任务,微任务执行完毕后,再回到宏任务中进行下一轮循环。...,而在浏览器不崩溃的前提下,通过执行栈与事件队列在宏任务与微任务中左右横跳,从而令浏览器事件不形成死锁,保证永不阻塞。

    4K40

    微信终端自研C++协程框架的设计与实现

    上图展示了非对称协程调用和函数调用的相似性,详细的时序如下: 调用者调用 co_create() 创建协程,这一步会分配一个单独的协程栈,并为 func 设置好执行环境 调用者调用 co_resume...() 启动协程,func 函数开始运行 协程运行到 co_yield(),协程挂起自己并返回到调用者 调用者调用 co_resume() 恢复协程,协程从 co_yield() 后续代码继续执行 协程执行完毕...,返回到调用者 如上图所示,有意思的是,如果一个协程没用调用 co_yield(),这个协程的调用流程其实跟函数一模一样,因此我们经常会说:函数就是协程的一种特例。...通过上面的示例可以看出,使用 co_create() 创建协程后,可以通过不断调用 co_resume() 来驱动协程的运行,而协程函数可以随时调用 co_yield() 来挂起自己并将控制权转移给调用者...Linux 车机微信客户端,我们通过实现自定义调度器让协程运行在 UI 框架的消息循环中,得以方便地在协程中访问 UI。

    2.4K31

    微信终端自研 C++协程框架的设计与实现

    上图展示了非对称协程调用和函数调用的相似性,详细的时序如下: 调用者调用 co_create() 创建协程,这一步会分配一个单独的协程栈,并为 func 设置好执行环境 调用者调用 co_resume(...) 启动协程,func 函数开始运行 协程运行到 co_yield(),协程挂起自己并返回到调用者 调用者调用 co_resume() 恢复协程,协程从 co_yield() 后续代码继续执行 协程执行完毕...,返回到调用者 如上图所示,有意思的是,如果一个协程没用调用 co_yield(),这个协程的调用流程其实跟函数一模一样,因此我们经常会说:函数就是协程的一种特例。...通过上面的示例可以看出,使用 co_create() 创建协程后,可以通过不断调用 co_resume() 来驱动协程的运行,而协程函数可以随时调用 co_yield() 来挂起自己并将控制权转移给调用者...Linux 车机微信客户端,我们通过实现自定义调度器让协程运行在 UI 框架的消息循环中,得以方便地在协程中访问 UI。

    1.7K31

    python中如何用列表+yield打破内卷的递归

    当函数中再次调用自身,即为递归 小伙在自己电脑上验证一番,发现确实可以达到要求。自信满满上传到网站上,却提示:"调用栈溢出!" 这就是递归的缺点,太内卷(内耗严重)了。...这是递归的退出条件,必须保证递归存在退出条件,否则就是死循环 在 python 中,函数的调用信息保存在一个叫帧的东西里面,我以前就有相关文章讲解,相关链接放在文末 这就是调用栈发挥作用的时候。...首先进入的东西,反而比后来进入的东西,要靠后才能出去。 那么,为什么说递归太"内卷"了?因为如果文件夹层级很深,那么调用栈就会堆积大量的调用信息,而调用栈的容量有限,很容易出现栈溢出。...用 list 保存,可存放容量比调用栈容量大得多” ---- 用 list 模拟栈 回到一开始的思路: 这是一个不确定结束条件的循环,不能使用确定性条件的 for 循环 修改为无限循环 行3:创建一个...请把函数中对路径的处理代码移除,又能保证调用者可以灵活使用" 小伙子随便想一下,就可以想到3种实现方式: 用一个 list 保存结果,最后返回 函数新增一个参数,是一个"可调用"的对象,让调用者定义处理函数

    1.7K20
    领券