# 玄铁类型系统哲学设计

是由两套方案组成:

1. 多档开关——在执行编译指令时加入指令参数`--严格、--禁止、--默认`  即可切换编译器语法检查等级,具体分级制度如下
   - 错误等级:
     - 宽松级:未使用的变量  |  静默处理
     - 警告级:隐式类型、若抑否逻辑表达式出现多个 `否` 编译器会只采用第一个否、隐式动态、可推断未声明  |  编译期输出警告,强烈建议开发者修复这个问题
     - 错误级:完全错误的语法  | 编译器完全退出并中断编译任务
   * 默认:按原分级处理(宽松→静默,警告→提示,错误→中断)
   * 严格:所有等级提升一档(宽松→警告,警告→错误,错误→错误)
   * 禁止:所有非错误提升为错误(宽松→错误,警告→错误,错误→错误)
2. 项目配置文件——在项目根目录放一个 `玄铁.配置.toml`
   ```
   [编译]
   严格度 = 禁止
   警告即错误 = ["隐式类型", "未使用变量"]
   忽略警告 = ["注释格式"]

   [版本]
   玄铁版本 = "0.18"
   ```
  当配置和命令行冲突时怎么办?请看配置优先级
   - 配置优先级(从高到低):
     - 命令行参数 > 项目配置文件 > 编译器默认值
     - 当命令行参数显式填写了严格声明,那么就使用严格模式编译
  `"隐式类型"` 究竟指什么?变量没标注?参数没标注?返回值没标注?
   - **"警告码"机制**:
     ```
     警告 W001 - 隐式类型(变量未标注)            [宽松]
     警告 W002 - 隐式类型(参数未标注)            [警告]
     警告 W003 - 隐式类型(返回值未标注)          [警告]
     警告 W004 - 逻辑语法(多个"否"分支)          [警告]
     警告 W005 - 弱引用语法(缺少可空修饰 ?)       [警告]
     警告 W006 - 路径规范(斜杠混用)              [警告]
     警告 W101 - 未使用变量                        [宽松]
     警告 W102 - 未使用导入                        [宽松]
     警告 W201 - 注释格式不规范                    [宽松]
     警告 W401 - 循环引用(强引用环)              [警告]
     ```
   - 配置文件里可以用警告码或类别名:
      ```
      警告即错误 = ["W001", "W002"]    # 精确控制
      # 或
      警告即错误 = ["隐式类型"]         # 类别一键控制(包含所有 W00X)
      ```
  怎么在源码里局部抑制警告?
   - **注解式**:在变量前添加 `@允许(未使用变量)` 即可抑制警告

    // 注解式(跟 Rust/TS 一致)
    @允许(未使用变量)
    设 x = 5
    
3. 等级可见可对话 
警告输出里要带等级信息:
```
警告 [warning-implicit-type] (严格度 严格):第 23 行
  参数 n 缺少显式类型注解
  推断结果:整
  修复建议:函 斐波那契(n: 整): 整 { ... }
  这个警告在严格度 [严格] 下会成为错误。
```
    
---

## 编译期错误与运行时诊断明细(v0.18.x 强化)

错误级诊断统一格式:`类别: [行:列] 描述`,非零退出码中断编译。当前覆盖:

| 错误类别 | 触发示例 | 诊断输出示例 |
|---------|---------|-------------|
| 解析错误 | 未闭合的块、非法前缀 | `解析错误: [行:2, 列:1] 期望当前标记为 右花括号,但得到 空` |
| 未知标识符 | `设 x = 未定义变量 + 1` | `编译错误: [1:7] 未知标识符 '未定义变量'` |
| 块级可见性 | `若 c { 设 v = 1 }` 后在块外 `示(v)` | `编译错误: [行:列] 变量 'v' 是在代码块(若/否/循环等)内声明的,块外不可见` + 「把声明提到块外或把使用移进块内」提示 |
| 参数个数不符 | `函 f(a,b){...}` 后 `f(1)` | `编译错误: [2:8] 函数 'f' 声明需要 2 个参数,但调用给了 1 个` |
| 类型注解冲突 | `设 x: 整 = "字符串"` | `编译错误: [1:1] 类型注解冲突: 声明为 '整',但赋的值是 '字'` |
| 模块路径不存在 | `引 "./不存在.xt" 予 X` | 列出源文件、引入路径、解析后绝对路径与修正提示 |

运行时诊断(同样遵循「宁可报错退出,不静默」):

| 运行时错误 | 原行为 | 现行为 |
|-----------|--------|--------|
| 调用不存在的方法 | 段错误 | `运行时错误: 调用了对象不存在的方法: 'xxx'` + 拼写提示 |
| 对整数/空等访问成员 | 段错误 | `运行时错误: 对非对象值访问成员 'xxx'` + 保护建议 |
| 对非字符串值调用字符串方法 | 段错误/静默返回错值 | `运行时错误: 对非字符串值调用字符串方法 '替换'` + 「结果 对象先判 .成功 再取 .值」提示 |
| fiber 池耗尽/定时器溢出 | 段错误/静默丢失 | 显式错误信息并退出 |

另有**编译提示**(不中断):当异步块的循环体内含挂起点(等待/收/发/选/时.睡)时,编译器会提示该块已按线程池任务编译,并给出 fiber 化建议(详见 [玄铁语言参考手册.md](./玄铁语言参考手册.md) 8.1.1 自动路由规则)。

> 注:未闭合文件曾导致解析器死循环并耗尽内存(无任何输出即退出),该缺陷已修复——现在会立即得到带行列号的清晰解析错误。

> **块级可见性的设计理由**:玄铁的 `设` 在符号层面是单链语义(同名即覆盖写,无块级遮蔽),但 ARC 按作用域层管理堆值——块内声明的堆值在块末即被释放清零。这曾造成「编译期可见、运行时已销毁」的最坏结局:块外引用读到 0,报的是谜之「对非对象值索引访问」。两害相权,编译器选择**在编译期直接拒绝**(报「块内声明块外不可见」并给出修法),把语义模糊地带变成明确规则:块内声明就是块内私有,要在块外用就先在外层声明。