-
Notifications
You must be signed in to change notification settings - Fork 0
Features
English | 中文
本页是全部已移植功能的机制说明。设计动机与实现细节见架构与设计。
每个样板在网络重算时被预编译为一段字节码(18 条指令:常量压入、四则运算、取整除法、子样板调用、库存提取、产物回插等)。执行模型为顺序执行的栈机:操作数栈上的数值是 BigInteger 无限精度,从根上排除溢出;0–1023 小值预分配 + 2 的幂快路径压低常规路径成本。整条链路零递归,天然免疫栈溢出。
首次执行某样板时以"1 次合成"为尺度捕获一次真实执行轨迹,记录成 bundle;此后对同一样板的任意数量需求直接按比例回放,复杂度 O(1)。子树需求以"needs"引用而非折叠,缩放时不会重复计数。bundle 按 grid 持久,跨请求复用。
缓存键是 (输出键, 样板编译字节码) 复合键:样板增删改后字节码指纹变化,旧 bundle 自动失效,同一输出键的多条样板可各自持有 bundle。回放前还校验"捕获时每个子调用解析到的样板"与当前解析一致(bundle 传递记录 subChoices),不一致即强制重新捕获——这堵住了上游 PatternRefreshReuse 类 bug 的 1.12 等价物:玩家改样板后,旧缓存把已不存在样板的冻结子树回放进新计划。
对斐波那契式指数需求链,VM 不是逐个展开节点,而是在样板关系图上做一次 O(patterns + edges) 的需求传播;多个样板共享的 DAG 节点只回放一次。这是"10^9 量级深链毫秒级完成"的基础。
-
A + B → 2A放大器:按净增量修正合成分配次数,自键收敛为一次性种子; - 无种子自引用恰好报缺 1 个启动单位,不多不少。
副产物闭环(如 A → 2B → E + D → A)按 working-capital 模型精确种子:前向模拟确定启动资金需求,配合死锁注入与 Tarjan SCC 判定。lossy 递减环(如 3A → 2B → D,A 每轮损耗)恰报缺 2 个启动量——每一类环都有可解释的最小种子语义。
纯换算环(价值在键之间转移而无净增减)用 BigInteger 分数环值做守恒校验;无种子时恰好报出"最小价值键"缺失,而非无意义地循环。
⚠ 1.2.0 起为实验性,默认关闭(配置项
ringSolverEnabled):卡死根因已在忠实 CPU 模拟器上定位——旧净额计划的交付被库存抵扣、环成员抽取被自身产出净掉,计划不带启动库存,t=0 死锁。现求解器按忠实语义重构:交付必须实际合成(真实任务忽略请求物品自身库存),环成员的净抽取与启动垫资全额入账 usedItems,闲置环的外耗也由闲置 bundle 计费;计划的任务序按模拟器验证过的执行顺序产出(在 CPU 严格任务序调度下无法自举的顺序被拒绝),催化剂种子同样计入启动垫资;全部环场景在模拟器上完整交付(详见 Roadmap 的 GAP-4b)。此外 1.2.0 起所有计划的任务序(不止折叠环)按样板依赖图的拓扑序构造——环保持探针验证过的顺序(环断在垫资边),深层计划按构造正确、无需跳过验证,忠实 CPU 复跑仅作兜底断言。实机验证进行中,欢迎开启反馈。2026-09-19 实机定案:AE2UEL 源码确认(CraftingCPUCluster.injectItems:265)——最终产物一经产出即计入交付、从不回流 CPU 库存(return leftover; // ignore it.);四类环形态与启动资本账单在真实服务器轨迹上逐项核实,并修复了 E-case 展开链一处实机黑洞(见「环外原料递归」)。
每轮净增产能的互环(4 灵魂 → 魂锭,1 魂锭 → 12 灵魂,每轮净赚 8 个灵魂)。该能力源自真实整合包游玩中遇到的盖亚之魂配方。原生规划器对这类环给不出任何计划:传播只沿根方向排程"分解侧",合成侧无人排程,CPU 在缺料处卡死,而原生递归规划更是直接栈溢出崩溃。环求解器将其代数折叠:按样板计数解出最小不动点(物料最小解),整个环折叠为单个毛流量 bundle(产物先入、原料后出,环内周转自洽),启动垫资单独精确披露。全家族覆盖:
- 副产物中间键:回路经过只以副产物存在的键(求解器 T4 回退使中间键入图);
- 环外原料环:环外原料(环内无生产者的投入)是普通配料需求,缺口诚实报缺;
- 副产物直接下单:直接下单副产物,请求按副产物产物槽折算轮数,并驱动整环放大;
- 跨环耦合链:消费者环先解,解算净抽取写回生产环的地板,供给环按放大后的真实需求定规模。
语义边界(务必了解):AE2UEL 的合成 CPU 对订单最终产物即产即交——一经产出立即计入交付、从不回流 CPU 库存(CraftingCPUCluster.injectItems :265)。由此:
- 直接下单环自身的净增益产物(如盖亚环下单盖亚之魂):产出的每一份都即刻离场,合成侧的消耗只能来自 job 启动资本,全额毛耗如实计账(订单 10000 魂即需 5000 魂启动,不足则精确报缺)——不存在"小库存跑出大订单";
- 增益经中间物流转的形态真自举:订单环的上/下游产物、副产物直接下单、跨环耦合链,环增益走的中间物不被虹吸、可回流自给,从极小垫资启动;存量成品还能作分解垫料单批放大(1 锭分解 → 12 魂 → 合成 3 锭);
- 单批内无再生:交付物不回流,启动资本随订单规模线性增长(净增益产物订单)。玩家可手动分批:每批交付回流网络后作为下一批垫料,批规模逐批放大,求解器披露的净增益率(每轮 +8 之类)即分批依据;引擎自动逐批推进已在路线图中,暂未实现。
净亏损环、纯换算环与催化剂循环不归环求解器管——它们分别由损耗环垫资模型、换算守恒校验与催化剂种子机制精确处理,门控确保各类环各归其位。
上游的 amount × ceil(times / uses) 摊销在 1.12 无法成立:AE2UEL 的 CPU 对
processing 样板按精确键提取,不会把磨损回流再吃回去,摊销计划会烧完预提工具后
中途停摆。1.2.0 起耐久工具输入按普通毛计费处理(每火一次消耗一把全新工具),
磨损回流作为惰性副产物随行;"输入被产出"的检测逻辑保留,用于催化剂种子与环
分析。详见差异与路线。
两个产物互为对方原料(如钢粉 ↔ 钢锭)且均无库存、无外部供给时,任一样板都不该被排程——原版会选中其中一个然后算出"缺自己"。VM 在解析期做配方交换图的 SCC 分析:自环恒剪;无种子、且环外无供给的 SCC 剪除;"外部供给"判定为环外键自身的生产样板输出含环成员(兄弟候选不算供环,副产物产入算供环)。种子环、外部供环、回流环全部保留;只剩一个候选时整段分析直接跳过;万一预剪误判,运行时守卫兜底。上游 v1.13.12 起主线亦内置同类能力(环感知样板选择,源自 GTL 版 CYCLE-AWARE);本移植为独立实现,10 项专项测试钉死行为。
(请求键, 数量, 样板集版本) → 计划 的缓存:同一请求重复计算直接命中(从毫秒级降到微秒级)。命中并不盲信——先对活库存复核(计划消耗必须仍充足、历史缺口必须已补齐),复核不过回慢路径重算。样板集任何变化经全局版本号(AtomicLong)感知,mixin 层在网格样板集 identity 指纹变化时 bump,bundle 缓存与计划缓存同步清空。删掉中间样板后,请求必须报缺而不是回放过期链。
多样板求解器的混合分配只有在一次真实重放确认严格更少总缺失后才被采纳;模型失真只会导致确认失败并保留原计划。求解器永远不可能让结果变差。
"算缺 → 补料 → 重算同一请求"的场景:含缺 bundle 的缺口键在新库存下可解时自动重执行,不再回放过期缺口。
多样板分配(见求解器专页)
同一产物存在多条样板时,贪心单选可能对某叶子超量需求。VM 在报缺时启动求解器:枚举 → 拆分权重局部搜索 → 合成虚拟样板表达混合配比(如 5 次合成 = 4×样板A + 1×样板B),确认门把关。上游自 v1.9.6 起唯一遗留的 FALSE_POSITIVE(multi-dag/fibonacci/minimum)由此零缺口关闭。
流体以假物品键表示,编译期做 drop 规范化(配方里的包形式 ↔ 网络监控的 drop 形式),mB 数量承载于 AE 栈大小。原生流体通道优先作为权威源,AE2FC 自身 item 通道的假条目被排除以避免重复计数。深层流体子样板(可合成流体 + 部分库存)可解析。
防御性递归解包 Scaled* 类"翻倍/缩放"包装样板(反射 getOriginal,深度上限 8):字节码与计划键锚定到原样板,第三方缩放附属即插即兼容。
替换组 + FUZZY_SLOT 槽位标记;处理配方默认同物品模糊族。精确槽与模糊槽的需求分离:替换品库存只满足模糊槽需求,精确槽绝不吞替换品。模糊族查询有两层按键缓存(sandbox 族列表 + VM 合成族 = 替换组 ∪ NBT 族),模糊场景从 17.7ms 降到 4.75ms。
槽位替代只属于合成样板(1.2.0 收窄):AE2UEL 把替代开关硬性绑在合成样板上(canSubstitute = isCrafting && nbt,PatternHelper :87),CPU 也只在合成分支查找替代——处理样板的槽位恒为精确键。编译器遵循同一语义:处理样板的槽位不再替代填充,替代品库存不能满足其槽位,缺料如实报缺(此前版本会产出真实 CPU 无法执行的计划并在 t=0 死锁)。合成样板的替换组行为不变;升级后个别此前"可合成"的请求可能改为诚实报缺一项。
模糊族的边界 = 同物品 + 同 damage + 不同 NBT(1.21 上游的 NBT 容差语义;1.12 的 damage 是物品身份——热力材料 134 铂锭绝不容差给 166 流明锭,这是实机验证揪出的移植语义修正);AE2FC 流体键的 NBT(FluidName)即身份,模糊族恒为空,流体只走精确键与 packet-key 索引。
环折叠后的环外消耗(如盖亚环的泰拉钢)若有自己的配方,则递归展开进它自己的生产样板:每一层注入前模拟库存、只为缺口排程,后序注入(输入的生产者先于自身入计划,保证重放应用顺序),回路重访被切断、回落为诚实报缺,无配方键保持原料级报缺(保守回退)。实机盖亚轨迹暴露过单层展开的缺陷——注入放大器自身的 mana 输入从 used 与 missing 表中同时消失(不可调度的静默黑洞,被常驻不变量审计以 MISSING-COVERAGE/INPUT-REACH 揪出)——已改为递归修复。
VM 计划直接构建 LiteCraftTreeNode 显示树(@Pseudo mixin),AE2CT 的合成预览保持可用。
-
AE2VMCrafting.isLoaded()/calculateSync()(同步 calculate;上游为 CompletableFuture 形态,见差异说明) -
getBatchRemainder():请求超过 Long.MAX_VALUE 时的余量 -
pickBestPattern最小输出守卫、ignore-fix、T1 精确 / T3 模糊解析
机器源的自动下单默认全部由 VM 规划——原生树无法承载净增环与流体样板,缓存指令器一类设备若走原生树会在这些网上静默失败(人工下单正常而自动不下单的根源)。极少数需要原生树结构的外来规划器用配置 nativeTreeSourceMarkers(类名/包名子串)排除,模组显式调用 AE2VMCraftingRegistry.register 始终赢回 VM。
网格重算时全量预编译新样板(CraftingGridCacheMixin),把首次请求的编译开销提前到样板变更时刻。
VM 无法处理的任何情况自动回退原生递归树;proxyEnabled 配置整体开关。
相关链接