Files
kyugao ec02a791ee 迭代22+23: 策略tab静态化 + 计算字段(数字/判定型)+ 网格超市信号字段
- R-027 静态化:策略恒为内置两项(不可增删改名,保留显隐/排序);设置页移除「策略分组」;
  字段配置入口迁到策略 tab 内「列设置」旁(FieldConfigDialog + schema-update 单策略写入)
- R-026 计算字段:自写公式引擎(中文变量、四则/括号/round·abs·min·max、缺值短路→—)+
  变量目录(行情/合约/持仓/自定义字段)+ strategy-positions 逐行现算(只读内存缓存,不落库、列只读)
- R-028 判定型:比较运算 + and/or + inferResultKind + 结果类型一致性校验 + 判定列 ✓/— 渲染;
  网格超市落地 可下空单=涨停价>基准值+网格大小、可下多单=跌停价<基准值-网格大小
- 变量选择改标签平铺(老师反馈);公式手册 docs/99-其他材料/计算字段公式说明.md
- 约束同步:产品约束-002/003/004/009/013/014、技术约束-014/015/022/023/024、UI约束-002/003/005/008
- 回归:新增 test-r026/test-r027,更新 r011/r013/r017,17 个脚本全绿;typecheck/build 通过
2026-09-10 14:05:06 +08:00

152 lines
9.0 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# 计算字段公式说明
> 适用:策略 tab →「字段配置」→ 添加/编辑字段 → 类型选「**计算**」
> 版本:2026-09-10R-026 计算字段 + R-028 判定型扩展)| 本文档与实现行为逐条对齐(已实机核对)
## 一、一句话
计算字段 = **你写一个公式**,服务端按**每个持仓行**实时算出一个值填到该列:公式里可以引用
**行情 / 合约信息 / 持仓账本 / 本策略手填字段**四类数据。值**不落库**、列**只读**、数据缺失时显示 `—`
## 二、结果类型(先选这个)
字段表单「**结果**」下拉决定列的呈现方式,且**必须与公式形态一致**(服务端校验,不一致直接拒绝保存):
| 结果类型 | 公式形态 | 列上显示 | 可配项 |
|---|---|---|---|
| **数字**(默认) | 算式,如 `(现价 - 成本价) × 份额` | `700.00 元`(小数位 + 单位) | 小数位 0–4(默认 2)、单位 |
| **判定** | 顶层是比较,如 `涨停价 > 基准值 + 网格大小` | 满足 → `✓ 可下空单`(绿);不满足/缺数据 → `—`(灰) | 单位、小数位不适用(自动隐藏) |
- 判定列文字 = 该字段的**展示名**(所以展示名建议直接写成规则名,如「可下空单」);
- 「不满足」与「数据缺失」目前**都显示 `—`**(避免把「没数据」误读成「不满足」)。
## 三、可用变量(写中文名即可;点「+ 插入变量」自动插入)
| 分组 | 变量 | 含义 / 来源 |
|---|---|---|
| 行情 | `现价` `昨收` `今开` `最高` `最低` `成交量` `成交额` | 盘口内存快照(服务端 5s 刷新) |
| 合约 | `涨停价` `跌停价` | 合约信息(按交易日,当天不变) |
| 持仓 | `份额` `成本价` `最后成交价` | 持仓账本:本策略分配份额 / QMT 成本价 / 最后一笔实际成交价 |
| 自定义字段 | 本策略**手填字段的展示名**(如 `基准值` `网格大小` `网格交易量` | 该持仓行手填的值 |
规则与注意:
1. **变量名 = 内置名(上表固定 12 个)或手填字段的展示名**。手填字段**改名后**,引用它的公式会失效
(该列变 `—`,再保存字段时会提示「未知变量」),把公式里的变量名同步改成新名字即可;
2. 字段展示名**不得与内置变量名冲突**(不能建一个叫「现价」的字段),同策略内展示名不得重复;
3. **计算字段不能被另一个公式引用**(零循环依赖):公式里写另一个计算字段的名字会报「未知变量」;
4. 手填字段的**非数字值**参与运算按「无值」处理(空文本 → 该行 `—`;布尔按 1/0)。
## 四、运算符
| 类别 | 写法 | 说明 |
|---|---|---|
| 四则 | `+ - * / ` | 全角 `× ÷ ` 同样可用 |
| 括号 | `( )` | 全角 ` ` 同样可用 |
| 比较 | `> < >= <= == !=` | 全角 `≥ ≤ ≠ ` 同样可用;`==` 是**精确相等**(无容差) |
| 逻辑 | `and` / `or`(也可 `&&` / `||` | 判定型专用,如 `A > 1 and B < 2` |
| 一元负 | `-现价` | — |
**优先级**(低 → 高):`or``and` → 比较 → 加减 → 乘除 → 一元负 → 括号。拿不准就加括号,最稳。
## 五、函数(只有这 4 个)
| 函数 | 参数 | 例子 | 结果 |
|---|---|---|---|
| `round(值, 位数)` | 1–2 个;位数 0–10(负数按 0 处理) | `round(106.666, 2)` | `106.67` |
| `abs(值)` | 恰好 1 个 | `abs(成本价 - 现价)` | `0.7` |
| `min(...)` | ≥1 个 | `min(涨停价, 现价 * 1.05)` | 取小 |
| `max(...)` | ≥1 个 | `max(0, 现价 - 成本价)` | 取大(不小于 0 |
## 六、计算规则与「缺值」语义
- **缺值短路**:公式里**任一变量没有数据**(无行情、无合约信息、手填字段为空)→ 整行结果为空 → 列显示 `—`
(不会显示 0 或 NaN,也不会报错、不会炸表);
- **除零 / 结果非有限数** → `—`
- **浮点归一**:自动消除浮点噪声(不会出现 `0.7000000000000002` 这种值);
- **限制**:公式 ≤ **500 字符**、嵌套 ≤ **32 层**(超出提示「公式过长 / 过于复杂」);
- **安全**:自写解析引擎,不支持 `eval`,除四则/比较/逻辑/这 4 个函数外没有任何能力(不能读写文件或网络)。
## 七、列上怎么显示
| 场景 | 显示 |
|---|---|
| 数字型有值 | 按「小数位 + 单位」显示(如 `6.67 %``700.00 元`;单位留空则只显示数字) |
| 判定型满足 | `✓ <字段名>`(绿),如 `✓ 可下空单` |
| 判定型不满足 / 数字型无值 | `—`(灰) |
| 已清仓的历史持仓行 | `—`(不做历史时点计算) |
| 表头 | 列名前带 `ƒ` 标记;悬停列头/单元格可见公式原文(`= 公式` |
| 刷新 | 随策略持仓接口轮询刷新(行情服务端 5s 更新;列值是「计算快照」,不做价格闪烁) |
## 八、常用公式(可直接抄)
### 网格超市
| 用途 | 结果类型 | 公式 |
|---|---|---|
| 可下空单 | 判定 | `涨停价 > 基准值 + 网格大小` |
| 可下多单 | 判定 | `跌停价 < 基准值 - 网格大小` |
| 触到上边界 | 判定 | `现价 >= 网格上边界` |
| 跌破下边界 | 判定 | `现价 <= 网格下边界` |
| 距上边界 % | 数字(单位 %) | `(网格上边界 - 现价) ÷ 现价 × 100` |
| 每格金额 | 数字(单位 元) | `网格交易量 × 网格大小` |
| 本行网格占用 | 数字(单位 元) | `现价 × 份额` |
| 空单且未触上边界(组合) | 判定 | `涨停价 > 基准值 + 网格大小 and 现价 < 网格上边界` |
### 手动做T / 通用
| 用途 | 结果类型 | 公式 |
|---|---|---|
| 浮动盈亏 | 数字(元) | `(现价 - 成本价) × 份额` |
| 盈亏比例 | 数字(% | `round((现价 ÷ 成本价 - 1) × 100, 2)` |
| 市值 | 数字(元) | `现价 × 份额` |
| 距涨停 % | 数字(% | `(涨停价 - 现价) ÷ 现价 × 100` |
| 成本上方空间 | 数字(元) | `max(0, 现价 - 成本价) × 份额` |
| 盈利中 | 判定 | `现价 > 成本价` |
| 成本上方且未涨停 | 判定 | `现价 > 成本价 and 现价 < 涨停价` |
| 相对 T 仓成本盈亏 | 数字(元) | `(现价 - T仓成本价) × 份额` |
## 九、保存校验与报错对照
保存字段时服务端会**先校验语法与变量**,不通过直接拒绝(公式框描红 + 提示,表单不关闭):
| 提示 | 原因 | 怎么办 |
|---|---|---|
| `公式不能为空` | 公式为空 | 填公式 |
| `公式不完整` / `缺少右括号` / `意外的符号` / `无法识别的字符` | 语法错 | 检查括号与运算符是否写全 |
| `未知变量『xx』——该字段已删除或名称有误` | 变量名不对(或引用了计算字段) | 用「+ 插入变量」插入,或核对字段展示名 |
| `未知函数『xx』(可用:round/abs/min/max` | 用了未实现的函数 | 只用这 4 个 |
| `函数『xx』参数个数不对` | 参数多/少 | 见第五节 |
| `变量名『现价』与内置变量冲突,请修改字段展示名` | 字段名撞内置变量 | 改展示名 |
| `字段展示名重复: xx` | 同策略两字段同名 | 改其一 |
| `公式过长(上限 500 字符)` / `公式过于复杂(嵌套过深)` | 超限 | 拆成两个字段 |
| `结果类型选了「判定」,但公式没有比较运算(如 涨停价 > 基准值 + 1)` | 结果类型与公式形态不符 | 改结果类型为「数字」,或把公式写成比较 |
| `公式结果是判定,请把「结果类型」改为「判定」` | 同上(反向) | 把结果类型改为「判定」 |
配置时可点「**试算**」:服务端拿该策略**一行真实持仓**当场算给你看
(判定型显示 `✓ 满足 / — 不满足`;无持仓提示「暂无可试算的持仓数据」)。
## 十、常见问题
**Q:为什么整列都是 `—`**
按序排查:① 该 code 暂无行情/合约快照(等 5s 同步,或点会话头部行情灯立即同步);
② 公式用到的手填字段该行没填值;③ 公式里有除零;④ 公式引用了已删除/改名的字段。
**Q:能不能写条件分支(三态:空 / 多 / 观望)?**
目前不支持 `if`/三元表达式;判定型只覆盖「满足 / 不满足」两态。要一列表达三态时,
可先用两个判定字段(`可下空单` + `可下多单`)代替 —— 两个都为 `—` 即观望。
**Q:能不能跨行求和(本策略总盈亏)?**
不能——公式是**逐行**计算,只看得到本行数据。
**Q:格子能手动改吗?**
不能,计算字段**只读**;手填字段才能在格子里点击编辑。
**Q:单位参与计算吗?**
不参与,只影响显示(拼在值后);判定型不需要单位。
## 十一、暂不支持(明确边界)
条件分支(`if`/三元)、`not` 取反、判定与数字混用的单字段、跨行聚合(求和/平均)、历史持仓行时点计算、
策略以外的数据集(账户域持仓、交易记录聚合——尚未接入为变量)。