AI开发C语言应用按步走,表达式计算器calc的第十一步,Token 联合体、哈希表满报错、批处理变量赋值

📅 2026/7/24 14:01:47
AI开发C语言应用按步走,表达式计算器calc的第十一步,Token 联合体、哈希表满报错、批处理变量赋值
calc11 — Token 联合体、哈希表满报错、批处理变量赋值1. 概述本次迭代基于 suggestions.md 中的建议完成了三项代码改进Token 联合体— 将value和name字段合并为联合体减少内存占用哈希表满报错— 变量符号表满时输出错误提示而非静默丢失批处理变量赋值—./calc x 5现在可直接在批处理模式中赋值2. 变更清单文件操作说明parse.h编辑Token 结构体改用联合体union { double value; char name[32]; } data新增MAX_NAME 32宏parse.c编辑tok.value→tok.data.valuetok.name→tok.data.nameeval.c编辑t.value→t.data.valuet.name→t.data.namesym.c编辑sym_set循环结束后添加满表报错symbol table is fullmain.c编辑parse_and_eval增加is_assignment检测支持批处理变量赋值test.expr编辑x5/y10从错误用例改为成功用例退出码 03. Token 联合体3.1 改造前typedefstruct{TokenType type;doublevalue;// 每个 Token 占 8 字节intcol;charname[32];// 每个 Token 占 32 字节}Token;// 总计 48 字节3.2 改造后#defineMAX_NAME32typedefstruct{TokenType type;intcol;union{doublevalue;// TOKEN_NUMBER 时使用charname[MAX_NAME];// TOKEN_IDENTIFIER 时使用}data;}Token;// 总计 40 字节节省 8 字节value和name共享同一块内存type字段决定访问哪个成员。3.3 涉及的文件所有访问tok.value/t.value和tok.name/t.name的地方均改为tok.data.value/t.data.value和tok.data.name/t.data.name涉及parse.c和eval.c。4. 哈希表满报错在sym.c的sym_set函数中线性探测循环结束后添加/* 表满 */fprintf(stderr, error: symbol table is full, cannot set %s\n,name);此前sym_set在 256 个桶全满时静默返回赋值丢失且无任何提示。5. 批处理变量赋值5.1 改造前parse_and_eval仅支持普通表达式求值./calc x5报错退出。5.2 改造后parse_and_eval中调用is_assignment检测赋值模式staticintparse_and_eval(constchar*input){charvar_name[32];if(is_assignment(input,var_name,sizeof(var_name))){constchar*pinput;while(*p*p!)p;constchar*rhsp1;while(*rhsisspace((unsignedchar)*rhs))rhs;doubleresult;if(eval_expr(rhs,result)!0)return1;sym_set(var_name,result);printf(%g\n,result);return0;}doubleresult;if(eval_expr(input,result)!0)return1;printf(%g\n,result);return0;}5.3 使用示例$ ./build/calcx 5 38注意批处理模式每次调用是独立进程变量表不跨进程持久化。链式变量引用如y x * 2需在 REPL 会话中完成。6. 目录结构calc/ ├── Makefile ├── parse.h / parse.c # Token 联合体 ├── eval.h / eval.c ├── sym.h / sym.c # 哈希表满报错 ├── main.c # 批处理变量赋值 ├── test.expr # 29 个测试用例 ├── doc/ │ ├── readme.md │ ├── calc1.md ~ calc10.md │ └── calc11.md # 本次构建 └── build/ └── calc7. 测试验证$maketestcalc — 测试套件PASS[1](90-18)/315 →39... PASS[23]x5→5PASS[24]y10→10...29passed,0failed,29total批处理变量赋值测试通过x5输出5y10输出10。