4、撮合引擎核心逻辑:价格优先、时间优先原则、连续竞价与集合竞价
好,咱们今天聊撮合引擎。这是整个交易系统的灵魂,也是我当年踩坑最多的地方。
说白了,撮合引擎就干一件事:把买单和卖单对上。但怎么对上,对上的顺序是什么,这里面的门道可不少。我个人习惯把撮合逻辑拆成两个维度来看:规则和模式。
4.1 价格优先、时间优先:铁律中的铁律
先讲规则。全球主流交易所,无论股票、期货还是数字货币,撮合的第一原则就是价格优先,第二原则是时间优先。
- 价格优先:买单出价高的排前面,卖单出价低的排前面。说白了,买方谁更想买,谁先成交;卖方谁更想卖,谁先成交。
- 时间优先:价格相同的情况下,谁先挂单谁先成交。这个好理解,先来后到嘛。
嗯,这里要注意:价格优先的优先级高于时间优先。也就是说,哪怕你晚了一秒钟,但只要你的出价比别人高,你就能插队到前面去。我曾经在项目中遇到过客户质疑:“为什么我的单子挂了一整天都没成交,别人刚挂就成交了?” 答案很简单——别人出的价格更好。
4.2 连续竞价:日常交易的主战场
连续竞价,就是咱们平时说的“盘中交易”。交易时间内,只要买卖双方价格能对上,就立刻成交。
它的工作流程是这样的:
- 系统收到一个买单(或卖单)。
- 从对手方队列里,按价格优先、时间优先的顺序,找出能匹配的单子。
- 能匹配就成交,不能匹配就挂到队列里等着。
- 重复这个过程,直到没有单子能匹配为止。
举个例子:
| 方向 | 价格 | 数量 | 时间 |
|---|---|---|---|
| 卖单A | 10.00 | 100 | 09:30:01 |
| 卖单B | 10.01 | 200 | 09:30:02 |
| 买单C | 10.00 | 150 | 09:30:03 |
买单C进来,价格10.00。它先跟卖单A比,价格一样,时间上卖单A更早,所以成交100。剩下50股,继续跟卖单B比?不行,卖单B价格10.01,比买单C的10.00高,买不起。所以买单C剩下的50股就挂在买单队列里等着。
你看,连续竞价的核心就是“来一个,比一个”。我建议你在设计时,把买卖双方的订单簿(Order Book)维护成两个有序链表,这样匹配效率最高。
4.3 集合竞价:开盘、收盘的定价艺术
集合竞价跟连续竞价完全不同。它不是“来一个比一个”,而是“攒一批,统一比”。
集合竞价通常用在开盘、收盘、以及盘中临时停牌后的复牌阶段。它的目标是找到一个成交量最大的价格,让尽可能多的单子成交。
流程是这样的:
- 收集一段时间内的所有买卖委托(比如开盘前9:15-9:25)。
- 系统不成交,只收集,所有单子都挂在队列里。
- 到时间点(比如9:25),系统统一计算出一个“集合竞价价格”。
- 所有在这个价格上能成交的单子,统一成交。
这个价格怎么算?我直接说结论:找到那个能让成交量最大的价格。如果有多个价格成交量一样大,那就取离上一笔成交价最近的那个。
举个例子:
| 价格 | 累计买单量 | 累计卖单量 | 可成交量 |
|---|---|---|---|
| 10.00 | 500 | 100 | 100 |
| 10.01 | 400 | 300 | 300 |
| 10.02 | 200 | 500 | 200 |
你看,10.01这个价格上,可成交量是300,最大。所以集合竞价价格就是10.01。所有买单价格≥10.01的,以及所有卖单价格≤10.01的,都按10.01成交。
4.4 两种模式的切换与衔接
一个完整的交易时段,通常是这样的:
- 开盘前:集合竞价(比如9:15-9:25)
- 开盘后:连续竞价(比如9:30-11:30, 13:00-15:00)
- 收盘前:有时也会有一次集合竞价(比如14:57-15:00)
这里有个细节:从集合竞价切换到连续竞价时,未成交的单子怎么办? 答案是:自动转入连续竞价队列。价格优先、时间优先的规则继续生效,但时间戳会保留集合竞价时的委托时间。
嗯,我建议你在设计系统时,把集合竞价和连续竞价做成两个独立的模块,中间通过一个订单状态机来衔接。这样逻辑清晰,也方便后期扩展。
4.5 核心逻辑流程图
下面我用一张SVG图,把整个撮合引擎的核心逻辑串起来。你一看就明白了。
这张图把整个流程串起来了。你仔细看,无论是集合竞价还是连续竞价,最终都会落到价格优先、时间优先这个核心规则上。只不过集合竞价是“先算后做”,连续竞价是“边来边做”。
好了,关于撮合引擎的核心逻辑,今天就聊这么多。记住:价格优先是灵魂,时间优先是保障,连续竞价和集合竞价是两种不同的实现方式。搞懂了这些,你就能设计出一个健壮的撮合系统了。