实盘第一天:边际是怎么被吃掉的
上线 13 小时,9 笔成交,手续费 $0.194。数字小得没有统计意义 —— 但这一天暴露了五个问题,全都是回测里看不到的那种。 其中三个是代码缺陷,一个是交易所规则的硬约束,还有一个是参数过松导致的、会持续腐蚀边际。
先看客观事实
跟的地址做的是 HYPE 的双向网格:常驻约十几张 33 枚的限价单, 买单铺在下方、卖单铺在上方,纯 maker(2000 笔成交里 0% 主动成交)。 我们按 1:33 缩放,他的每张 33 枚 = 我们的 1 枚。
| 时间 (UTC) | 动作 | 方向 | 数量 | 我们的价 | 他的价 | 手续费 |
|---|---|---|---|---|---|---|
| 03:51:49 | 建仓 | BUY | 3.0 | 89.157 | — | 0.05349 |
| 12:11:04 | 镜像 | SELL | 1.0 | 90.635 | 90.693 | 0.01813 |
| 14:26:16 | 镜像 | BUY | 1.0 | 88.449 | 88.462 | 0.01769 |
| 15:31:09 | 镜像 | BUY | 1.0 | 87.934 | 87.970 | 0.01759 |
| 15:31:09 | 镜像 | BUY | 1.0 | 87.916 | 87.949 | 0.01758 |
| 15:57:02 | 镜像 | BUY | 1.0 | 87.687 | 87.717 | 0.01754 |
| 16:38:22 | 镜像 | BUY | 1.0 | 87.017 | 87.013 | 0.01740 |
| 16:38:47 | 镜像 | BUY | 1.0 | 86.890 | 86.886 | 0.01738 |
| 16:44:50 | 纠偏 | BUY | 1.0 | 86.943 | — | 0.01739 |
镜像单挂了 19 张、成交 7 笔。 他的同期成交 7 笔,我们跟上 3、超时 1。仓位 3.0 → 9.0(目标 10.0)。
镜像侧的成交价几乎每一笔都比他的好 —— 买得低 1.5 ~ 4.1bp:
14:26 BUY 我们 88.449 他 88.462 +1.5bp
15:31 BUY 我们 87.934 他 87.970 +4.1bp
15:31 BUY 我们 87.916 他 87.949 +3.8bp
15:57 BUY 我们 87.687 他 87.717 +3.4bp
12:11 SELL 我们 90.635 他 90.693 −6.4bp ← 卖侧是负的
但最后那笔纠偏的代价,把前面省下来的全吃回去了。
问题一:镜像挂价的偏移,一次错过就是 13.5bp
这是这一天最实质的问题
完整的时序是这样的:
16:39:45 他在 86.826 成交(他加仓:297 → 330)
他的成交让目标从 9.0 变成 10.0
我们挂了一张镜像 BUY 在 86.77 ← 比他低 6.4bp
↓
币安的价格没有跌到 86.77,我们没成交
16:44:46 ⚠ 镜像:他在 86.826 成交 300s 了,币安没打到我们的 86.77,撤单交给纠偏
16:44:46 [实盘] 挂 BUY 1.00 @ 86.9430 | 他 330.00 目标 10.00 我 8.00 MIR+1.00
16:44:50 [实盘] 成交 BUY 1.00 @ 86.9430 | 我 9.00
他成交 86.826
我们的镜像 86.770 ← 比他好 6.4bp
实际成交 86.943 ← 比他差 13.5bp
为了省 6.4bp 挂了更低的价,结果多付了 13.5bp。 这是典型的逆向选择 —— 只在价格朝不利方向走的时候才吃不到。
我一开始的判断是「他的 maker 成交是 HL 那边的流,币安不一定有同样的对手盘」—— 把币安的分钟线拉出来之后,这个判断被推翻了:
全窗口(16:39~16:44)币安最低价 86.787
他的成交价 86.826 ← 够到了
我们的镜像价 86.770 ← 只差 1.7bp,没够到
币安的价格明明穿过了 86.826 还往下多走了 4bp。 所以不是「对面没有流」,是我们挂错了位置。
真正的原因在挂价的计算上:
我们的挂价 86.770 ÷ 他的 86.826 = 0.99936 → 下单时的 basis = −6.4bp
当时实际的 basis = +3.4bp
─────────
差 9.8bp
我们的镜像价是 他的价 × basis,而 basis 一直在变。
这张单是拿 9.8bp 之前的旧 basis 算出来的,而重挂阈值
reprice_bps = 30 意味着基差跑 10bp 不会触发重挂 ——
于是它就一直挂在偏了 6.4bp 的位置上,直到宽限期耗尽。
如果按当时的 basis 重算:86.826 × 1.00034 = 86.855
而全窗口最低价是 86.787 → 86.855 会被穿过 ✓ 会成交
所以这不是结构性的跨市场问题,是参数问题。 但那个参数有来历:配置注释写着「demo 基差 ±40bp 时 10 太敏感(每对平均撤换 53 次)」。 那是 demo 环境的经验,而主网的基差实测只有 ±4bp。
结论:重挂阈值很可能该收紧,但不能凭一次事件就改。
这正是偏差台账要做的事 —— 它会记录每次偏差的 drift_bps 和
end(he_filled / he_canceled / caught_up),
攒够样本才能同时回答「收紧到多少」和「收紧的换手代价有多大」。
可能的缓解方向(都还没验证,按代价排序):
- 缩短宽限期。现在是 300 秒,承担了 5.6bp 的中位漂移(HYPE 每小时波动 41bp,按 √t 缩放)。缩短到 60~120 秒可以减少漂移,但可能过早追价、多付 taker。
- 降低重挂阈值。现在基差变动超过 30bp 才重挂(早期设 10bp 时每对平均撤换 53 次,太频繁)。但阈值太松会让挂价长时间偏在错的位置 —— 这次就是偏了 6.4bp。
- 干脆用 taker 追。币安 taker 5bp < 这次的 13.5bp。如果漂移的期望大于手续费差,直接吃单更划算。
- 把宽度做成自适应的。用真实数据统计「错过率 × 漂移」和「挂宽 × 换手」的权衡 —— 但这需要样本。
问题二:保护止损被交易所价格带压成了「价格止损」
日志里有这么一行,值得单独拎出来:
保护止损单已挂:SELL @ 74.844
(距标记价 14.0%,触发时亏 $85)
[受交易所 ±15.0% 限制,挂不到 $2,332 的预算位]
设计意图是「亏掉本金 × 25% 就止损」,也就是 $2,332 的预算。 但止损价 = 标记价 − 预算 ÷ 持仓量 —— 我们能挂的仓位太小(9 枚 ≈ $780 名义), 算出来的止损价远在币安允许的 ±5% 价格带(PERCENT_PRICE,主网 ±5%)之外, 被钳制到交易所允许的最远处。
结果是:这道保险实际是一道 14% 的价格止损,不是 25% 的资金止损。
这意味着什么?HYPE 跌 14% 我们就被动平仓,而他会继续持有网格 —— 一个网格交易者的核心机制就是「下跌时不断加仓摊平」,我们却在半途被自己的保险踢出去。
这个偏差会随着仓位变大而消失(持仓够大时 25% 预算落在价格带内), 但在 1:33 这个缩放上,它一直有效,而且和跟单逻辑的目标是冲突的。
问题三:镜像成交记错了单号
第一笔镜像成交后,日志写着「费 未取到」。 查下来是记账时用了他的 Hyperliquid 单号,而手续费要用我们自己的币安单号去查 —— 拿 HL 单号查币安,永远查不到。
但这不只是手续费显示问题:
trades.csv 的 order_id 列存的是 HL 单号,
凡是按币安 orderId 关联的地方全部匹配不上。
其中一个是权益曲线的重建 —— 它拿这张表去和币安的成交记录求交集,
于是镜像成交被整段排除在跟单盈亏之外。
也就是说:账面上的「跟单累计盈亏」少算了 7 笔成交。
已修复(新增 o_oid 字段区分「他的单号」与「我们的单号」),并把已有记录补录回正确值。
问题四:磁盘上的代码 ≠ 进程里跑的代码
上面那个单号修复,部署之后并没有生效 —— 因为跟单引擎持有真实仓位, 部署脚本只同步文件、不自动重启进程。这是有意设计的(一次错误的重启会中断下单逻辑), 但它的副作用是:
磁盘上 mirror.py 已有修复
进程里 还是启动时加载的旧代码
结果 修复要等到下次重启才生效,而没人知道是什么时候
部署脚本现在会明确提示这件事,但这仍然是一个「部署成功」被误读成「已跑上新逻辑」的经典陷阱。 代码缺陷修复了,认知缺陷没有 —— 而对一个真实持仓的系统来说,后者更贵。
问题五:两个看板的成交表排序相反
「我方成交」最新在上,「对方成交」最早在上。逐行对比时, 同一行的两笔根本不是同一时间 —— 实测我方第 1 行是 10-01 16:44, 对方第 1 行是 09-28 19:21,差 3 天。
看的人会得出「成交时间差很大」这个错误结论。已修(统一为最新在上), 并给我方成交表加了「他价 / 价差」两列 —— 不用再去对方那张表逐行找了。
这一天的结论
9 笔成交、$0.194 手续费,统计上什么都说明不了。但五个问题里:
| 问题 | 性质 | 状态 |
|---|---|---|
| 镜像挂价偏移 → 错过 → 追价 13.5bp | 参数问题(重挂阈值过松) | 待数据 |
| 保护止损被压缩成 14% 价格止损 | 与跟单目标冲突 | 待决策 |
| 镜像成交记错单号 | 代码缺陷 | 已修,待重启 |
| 磁盘代码 ≠ 运行代码 | 流程/认知 | 已加提示 |
| 两张成交表排序相反 | 可用性 | 已修 |
回测里看不到的东西,实盘第一天就全部出现了。 这也是我坚持要先把「偏差台账」做出来的原因 —— 上面第一个问题该改到多少,只有攒够偏差事件的数据才能回答。 在那之前拍任何参数,都是在重复「用一个样本证明一个规则」的错误。
相关:一个零和市场的地形图 · 我怎么骗了自己两个月 · 实时看板