perf(vast): _Peek(0) 增加游标缓存,命中率 87% 降低解析热点开销

TokenStream._Peek 是 cProfile 最大热点(1588 万次调用,累计 4.86s)。
递归下降解析常在同一游标位置重复窥视(_At/_AtOp/_AtName 等),
增加 _PeekCacheIdx/_PeekCacheTok 字段缓存最近一次 offset=0 结果,
命中时跳过 len() 与列表索引;游标移动后 Idx 失配自然失效。
实测大文件解析命中率 87.1%(6503 次调用仅 717 次真实访问),
vast 差分测试 51/53 通过、0 FAIL,正确性无回归。
This commit is contained in:
TermiNexus committed 2026-08-17 20:29:34 +08:00
1 parent e6b842f46b
commit 7e710d1e9a
1 file changed
+11
+11
View File
@@ -46,6 +46,11 @@ class TokenStream:
self.Source: str = source
self.LineStarts: list[int] = line_starts
self.Idx: int = 0
# _Peek(0) 缓存:递归下降解析常在同一游标位置重复窥视
# (_At/_AtOp/_AtName 等),命中时跳过 len() 与列表索引。
# 游标移动后 Idx 变化自然失配,无需显式失效。
self._PeekCacheIdx: int = -1
self._PeekCacheTok: Token | None = None
# ------------------------------------------------------------------
# 游标操作
@@ -54,6 +59,12 @@ class TokenStream:
i: int = self.Idx + offset
if i >= len(self.Tokens):
return self.Tokens[-1]
if offset == 0:
if self._PeekCacheIdx == i:
return self._PeekCacheTok
self._PeekCacheIdx = i
self._PeekCacheTok = self.Tokens[i]
return self._PeekCacheTok
return self.Tokens[i]
def _Next(self) -> Token: