![bb07467b86a1331bd9fa360746c6ab25.png](https://i-blog.csdnimg.cn/blog_migrate/cffedc40f25ddae8d74c1421cb429b68.jpeg)
在阅读CTP API文档时,我们经常会遇到“回调”,“回调函数”。这里“回调”是什么呢?
![a5dd0e7852f1ba78ef2c4017e7543762.png](https://i-blog.csdnimg.cn/blog_migrate/0976020f53f3843668ea7834c9d3ee10.jpeg)
什么是回调
软件模块之间总是存在着一定的接口,从调用方式上,可以把他们分为三类:同步调用、回调和异步调用。
同步调用是一种阻塞式调用,调用方要等待对方执行完毕才返回,它是一种单向调用;回调是一种双向调用模式,也就是说,被调用方在接口被调用时也会调用对方的接口;异步调用是一种类似消息或事件的机制,不过它的调用方向刚好相反,接口的服务在收到某种讯息或发生某种事件时,会主动通知客户方(即调用客户方的接口)。回调和异步调用的关系非常紧密,通常我们使用回调来实现异步消息的注册,通过异步调用来实现消息的通知(比如CTP中的委托和成交回报)。同步调用是三者当中最简单的,而回调又常常是异步调用的基础,因此,下面我们着重讨论回调机制在不同软件架构中的实现。
![10a29c77005d7cca5066e7d887c3f54e.png](https://i-blog.csdnimg.cn/blog_migrate/3e734643db3c0b02dc0f213cf01f536f.jpeg)
对于一般的结构化语言,可以通过回调函数来实现回调。回调函数也是一个函数或过程,不过它是一个由调用方自己实现,供被调用方使用的特殊函数。
在面向对象的语言中,回调则是通过接口或抽象类来实现的,我们把实现这种接口的类成为回调类,回调类的对象成为回调对象。对于象C++或Python这些兼容了过程特性的对象语言,不仅提供了回调对象、回调方法等特性,也能兼容过程语言的回调函数机制。
我们可以打个比方,有一家旅馆提供叫醒服务,但是要求旅客自己决定叫醒的方法。可以是打客房电话,也可以是派服务员去敲门,睡得死怕耽误事的,还可以要求破门而入往自己头上浇盆水。这里,“叫醒”这个行为是旅馆提供的,相当于库函数,但是叫醒的方式是由旅客决定并告诉旅馆的,也就是回调函数。而旅客告诉旅馆怎么叫醒自己的动作,也就是把回调函数传入库函数的动作,称为登记回调函数(to register a callback function)。
![bbe9e90687038d6472edac768db5f590.png](https://i-blog.csdnimg.cn/blog_migrate/f74ed2dc00d3b8587ffd22e4773fcff7.jpeg)
C++例子
通俗理解就是,把一个函数作为参数传给另一个函数,第一个函数称为回调函数。这个被传入的参数其实是函数指针,即指向一个函数的指针(地址)。在Python中,指针的概念被淡化。我们可以先举个C++的例子:
编写一个计算函数computer,对于两个整数进行各种计算(通用的,什么计算都能做)。有一个形参是指向具体算法函数的指针,根据不同的实参函数,用不同的算法进行计算。
编写三个函数:求两个整数的最大值,最小值,和。分别用这三个函数作为实参,测试computer函数。
那么肯定有人会问,一个函数怎么可能做各种计算呢?——这个时候,我们在computer的形参中设置一个函数指针,每次调用的时候传递给它一个函数指针。
用函数名去初始化形参函数指针。这样的话,我们写computer函数的时候就只管说我要调用一个对两个整数做运算的函数,至于要做什么运算,只需要把代表这个运算的函数名传给我,我用函数指针来接收,用函数指针充当函数名,去调用函数体。这就是函数指针的好处,也就是函数回调。
![79b631fabc7d1283a733a00f993bdd9d.png](https://i-blog.csdnimg.cn/blog_migrate/4743c186fd119050a5fb93448dc57dbd.jpeg)
![3d65d000b39b658790201257a87d6c85.png](https://i-blog.csdnimg.cn/blog_migrate/d111b65319c6f4e0428051db69153573.jpeg)
Python例子
现在再说Python的情况:
类似上面,编写三个函数:求两个整数的最大值,最小值,和。分别用这三个函数作为实参,测试computer函数。在调用max,min,sum时,这三个函数就是此处的回调函数。
![8c1e721d2ce71cfcd7b64e3c9c4954b8.png](https://i-blog.csdnimg.cn/blog_migrate/37d733adf971a63a2c020de93519d19b.jpeg)
![da2a196d36de73b5c4f2c5e54a528324.png](https://i-blog.csdnimg.cn/blog_migrate/59ed8330bc7264fbfb61cfe09fbe6698.jpeg)
回调函数和普通函数在定义的时候没有什么区别,只有在调用时才看出来是不是回调函数,正常调用就是普通函数,作为一个函数的参数在需要的时候分情况调用,就是回调函数。
另外,回调函数还可以进行异步调用,即非阻塞调用,通常用在多线程或者多进程中。
— — — — — — E N D — — — — — —
往期文章:
Numpy处理tick级别数据技巧
真正赚钱的期权策略曲线是这样的
多品种历史波动率计算
如何实现全市场自动盯盘
AI是怎样看懂研报的
真格量化策略debug秘籍
真格量化对接实盘交易
常见高频交易策略简介
如何用撤单函数改进套利成交
Deque提高处理队列效率
策略编程选Python还是C++
如何用Python继承机制节约代码量
十大机器学习算法
如何调用策略附件数据
如何使用智能单
如何扫描全市场跨月价差
如何筛选策略最适合的品种
活用订单类型规避频繁撤单风险
真格量化回测撮合机制简介
如何调用外部数据
如何处理回测与实盘差别
如何利用趋势必然终结获利
常见量化策略介绍
期权交易“七宗罪”
波动率交易介绍
推高波动率的因素
波动率的预测之道
趋势交易面临挑战
如何构建知识图谱
机器学习就是现代统计学
AI技术在金融行业的应用
如何避免模型过拟合
低延迟交易介绍
架构设计中的编程范式
交易所视角下的套利指令撮合
距离概念与特征识别
气象风险与天气衍生品
设计量化策略的七个“大坑”
云计算在金融行业的应用
机器学习模型评估方法
真格量化制作期权HV-IV价差
另类数据介绍
TensorFlow中的Tensor是什么?
机器学习的经验之谈
用yfinance调用雅虎财经数据
容器技术如何改进交易系统
Python调用C++
如何选择数据库代理
统计套利揭秘
一个Call搅动市场?让我们温习一下波动率策略
如何用真格量化设计持仓排名跟踪策略
还不理解真格量化API设计?我们不妨参考一下CTP平台
理解同步、异步、阻塞与非阻塞
隐波相关系数和偏度——高维风险的守望者
Delta中性还不够?——看看如何设计Gamma中性期权策略
Python的多线程和多进程——从一个爬虫任务谈起
线程与进程的区别
皮尔逊相关系数与历史K线匹配
Python2和Python3的兼容写法
Python代码优化技巧
理解Python的上下文管理器
如何写出更好的Python代码?这是Python软件基金会的建议
评估程序化模型时我们容易忽视的指标
看看如何定位Python程序性能瓶颈
什么是Python的GIL
投资研究中的大数据分析趋势及应用
真格量化可访问:
https://quant.pobo.net.cn
![4b0566e3cf0d3e84f00954fd9f3352bb.png](https://i-blog.csdnimg.cn/blog_migrate/0944d77aa134d898d46159940b93b6f8.jpeg)
真格量化微信公众号,长按关注:
![617fd59d159f2ae94dc9d343e06df3ee.png](https://i-blog.csdnimg.cn/blog_migrate/1a95f1f49e90e4bb36ca5d91b6b6266a.jpeg)
遇到了技术问题?欢迎加入真格量化Python技术交流QQ群 726895887
![54d3718ce272ea7f595d94c16770be9a.png](https://i-blog.csdnimg.cn/blog_migrate/5188e4e9846138237935790eadffd831.jpeg)