词法分析器正则陷阱与编译原理三大核心模块避坑指南
简介本资源是面向高校计算机专业本科生的编译原理课程实验配套实现涵盖词法分析器、LL(1)语法分析器与LR(1)语法分析器三大核心模块完整支撑课程设计与实验教学需求。压缩包共52个文件含4个C源文件cpp与3个头文件h构成核心分析逻辑10组测试用例in/out用于验证功能正确性5份PDF文档提供实验说明与理论参考另有HTML前端界面、Makefile构建脚本及Git版本管理配置整体6.88MB结构清晰、开箱即用。已有1089人学习下载适合初学编译原理的学生理解分析器工作流程、调试状态转移与语法树构建过程。读者可直接运行图形化界面观察词法识别结果支持关键字、标识符、运算符、无符号数、字符串、字符常量及行间注释复现LL(1)预测分析表构造与LR(1)项目集规范族生成并通过源码级注释快速掌握各模块协作机制。1. 为什么写死正则就跑不通词法分析器——从 ZIP 包名看编译原理实验的三个“硬核关卡”你解压开编译原理实验之词法分析器、LL(1)语法分析器、LR(1)语法分析器.zip看到lexer.java、ll1_parser.java、lr1_table_gen.py这些文件名时第一反应可能是“哦又是王生原《编译原理第3版》第三章课后习题的延伸实现”。但真正动手改一行 token 规则、调一次 FIRST 集、手算一个 LR(1) 项目集规范族时90% 的人会在三处地方卡死词法分析器把当成两个、LL(1) 分析表里填了ε却没处理空产生式跳转、LR(1) 的 goto 表和 action 表对不上状态编号。这不是代码写得烂而是编译原理实验的底层逻辑——它不接受“差不多”只认“严格推导”。这个 ZIP 包不是成品工具而是一套可调试、可打断点、可手算验证的教科书级参考骨架词法分析器负责把源码切片成 token 流比如把int a 10;拆成(KEYWORD, int), (ID, a), (ASSIGN, ), (NUM, 10), (SEMI, ;)LL(1) 是递归下降的“确定性预言家”靠预测表决定下一步推导LR(1) 则是自底向上的“状态机工程师”用栈状态输入流三者协同归约。适合正在啃《编译原理第3版》第三章、做广州大学/哈工大/北航等高校编译原理实验课设的同学——你不需要造轮子但必须亲手拧紧每一颗螺栓。2. 词法分析器别让正则表达式成为你的玄学黑匣子词法分析器不是“写一堆正则然后 match 就完事”。它本质是确定性有限自动机DFA的手动或半自动实现。ZIP 包里的lexer.java或 Python 版lexer.py通常采用“状态转移表驱动”或“正则匹配优先级调度”两种主流结构。前者更贴近教材原理后者更易调试。我们以 Java 版为例拆解其核心骨架。2.1 从正则到状态机为什么[a-zA-Z_][a-zA-Z0-9_]*会漏掉main后的空格很多同学直接把教材里的正则丢进Pattern.compile()结果发现int main(){}被切成了(KEYWORD,int) (ID,main){}——{前少了LPAREN问题出在匹配粒度与贪婪策略。Java 的Matcher.find()默认按“最长匹配”找但词法分析要求最左最长maximal munch 优先级priority关键字if必须优先于 IDiff数字123必须优先于 ID123abc。// lexer.java 关键片段token 定义与匹配顺序不可颠倒 private static final String[] PATTERNS { [ \t\n\r\f], // 空白跳过不输出 token //.*|/\\*.*?\\*/, // 注释跳过 if|else|while|return|int|void, // 关键字高优先级 [a-zA-Z_][a-zA-Z0-9_]*, // 标识符低优先级 [0-9], // 整数 |!||||\\|\\|, // 双字符运算符必须放单字符前 [\\-*/%|!;{},()\\[\\]] // 单字符符号 };提示必须排在前面否则永远被拆成两个。这是词法分析器最经典的“翻车点”也是 ZIP 包里lexer.java的硬编码顺序——它不是随意写的而是严格按《编译原理第3版》P72 表 3.4 的 token 优先级排列。2.2 手动构建 DFA用二维数组替代正则适合教学验证当正则失效比如需要处理嵌套注释/ * ... * /就得回归 DFA。ZIP 包中常附带DfaSimulator.java其核心是状态转移表// stateTrans[i][j] 表示当前状态 i读入字符类型 j跳转到状态 k // 字符类型 j 映射0letter, 1digit, 2space, 3, 4, 5*, 6/, ... private static final int[][] stateTrans { {1, 2, -1, 3, 4, 5, 6}, // 状态0初始态 {-1,-1,-1,-1,-1,-1,-1}, // 状态1识别到字母开头 → 进入ID {-1,-1,-1,-1,-1,-1,-1}, // 状态2识别到数字开头 → 进入NUM {-1,-1,-1,-1, 7,-1,-1}, // 状态3读到 后又读到 → 进入 {-1,-1,-1,-1,-1,-1,-1}, // 状态4读到 → 单独 ASSIGN {-1,-1,-1,-1,-1, 8,-1}, // 状态5读到 * → 可能是 /* {-1,-1,-1,-1,-1,-1, 9}, // 状态6读到 / → 可能是 // // ... 后续状态省略实际需覆盖所有分支 };参数说明-1表示“非法转移”触发错误stateTrans[0][6] 6表示初始态读/进入状态6准备识别注释stateTrans[6][6] 9表示状态6再读/→ 进入//注释模式stateTrans[6][5] 8表示状态6读*→ 进入/*注释模式。这个表不是凭空写的而是根据教材 P68 的 NFA→DFA 转换步骤手算得出。ZIP 包里dfa_table.txt文件就是该表的文本化版本供你对照验证。2.3 词法错误处理如何让报错信息指向真实行号lexer.java中若只用String.split()或Scanner.next()错误位置会丢失。正确做法是维护lineNum和colNumprivate int lineNum 1; private int colNum 0; public Token nextToken() { while (pos input.length()) { char c input.charAt(pos); if (c \n) { lineNum; colNum 0; } else { colNum; } pos; // ... 匹配逻辑 } return new Token(TokenType.EOF, , lineNum, colNum); // 报错时输出 lineNum, colNum }关键细节colNum必须在pos前更新否则a10;的;会报错在列5而非列6。这是血泪经验——某次实验报告因报错位置偏移1列被扣分。3. LL(1) 语法分析器预测表不是查表游戏是 FIRST/FOLLOW 的落地验证LL(1) 分析器的核心是预测表M[A, a]其中A是非终结符a是终结符或$。ZIP 包中的ll1_parser.java通常提供parseTable[][]数组但它的生成逻辑才是重点。很多人直接抄表却不知为何M[Stmt, if] IfStmt而M[Stmt, id] AssignStmt。3.1 手算 FIRST 集为什么FIRST(E) {id, num, (}而不是{id, num, (, }教材 P102 给出 FIRST 计算规则但实操时极易忽略“递归传播”。以文法E → T E E → T E | ε T → F T T → * F T | ε F → id | num | ( E )计算FIRST(E) T E的 FIRST 是{}ε的 FIRST 是{ε}→ 所以FIRST(E) {, ε}。但FIRST(T)呢* F T的 FIRST 是{*}ε的 FIRST 是{ε}→FIRST(T) {*, ε}。关键陷阱FIRST(F)不含因为F的所有候选式都不以开头。只出现在E的候选式中与F无关。ZIP 包里的first_follow_calculator.py就是按此规则迭代计算的——它先初始化所有FIRST(X)为空集再循环扫描产生式直到无新元素加入。3.2 构建 LL(1) 预测表三步填表法避免 ε 冲突预测表填写有严格流程ZIP 包中buildParseTable()方法即遵循此逻辑对每个产生式A → α对每个a ∈ FIRST(α)置M[A, a] A → α若ε ∈ FIRST(α)对每个b ∈ FOLLOW(A)置M[A, b] A → α检查冲突若M[A, x]已有值再填入不同产生式 → 报错 “not LL(1)”# first_follow_calculator.py 片段填表核心逻辑 def build_parse_table(grammar): table {} for A in grammar.nonterminals: table[A] {} for prod in grammar.productions[A]: first_alpha first_of(prod.rhs) for a in first_alpha: if a ! EPSILON: if a in table[A] and table[A][a] ! prod: raise ValueError(fConflict in M[{A},{a}]: {table[A][a]} vs {prod}) table[A][a] prod if EPSILON in first_alpha: for b in follow_set[A]: if b in table[A] and table[A][b] ! prod: raise ValueError(fConflict in M[{A},{b}]: {table[A][b]} vs {prod}) table[A][b] prod return table参数说明EPSILON是预定义常量如或Nonefollow_set[A]是FOLLOW(A)集合由compute_follow()函数生成prod.rhs是产生式右部符号列表如[, T, E]冲突检测是硬性要求——如果M[Expr, (]同时被Expr → Term Expr和Expr → ( Expr )填入说明文法非 LL(1)必须改写如提取左公因子。3.3 递归下降解析器如何把预测表翻译成 Java 方法ll1_parser.java中parseExpr()方法不是凭空写的而是严格对应预测表// 对应 M[Expr, (] Expr → ( Expr ) void parseExpr() { if (lookahead.type TokenType.LPAREN) { match(TokenType.LPAREN); // 消耗 ( parseExpr(); // 递归调用 match(TokenType.RPAREN); // 消耗 ) } // 其他分支... }注意match()方法必须检查lookahead是否匹配不匹配则抛出ParseException(expected expected , got lookahead)。ZIP 包里ParseException类包含lineNum和colNum确保错误定位精准。4. LR(1) 语法分析器状态机不是魔法是项目集规范族的手算结果LR(1) 是编译原理实验的“珠峰”——它不靠预测而靠状态栈 输入流 action/goto 表的协同归约。ZIP 包中的lr1_parser.java或lr1_table_gen.py往往让人望而生畏但只要抓住“项目集规范族Canonical Collection”这一核心就能拨开迷雾。4.1 什么是 LR(1) 项目为什么E → •E, $和E → •E, )是两个不同项目LR(1) 项目形如A → α•β, a其中•是点a是向前看符号lookahead。a决定了归约时机。例如文法E → E E → E T | T T → T * F | F F → id | ( E )项目E → E•T, $表示已识别E下一个期待且整个句子以$结尾项目E → E•T, )表示已识别E下一个期待但整个句子以)结尾如(ET)中的E。关键区别向前看符号a不同导致它们属于不同状态。ZIP 包里的lr1_item.py类会显式存储dot_pos和lookahead确保项目比较时a参与哈希计算。4.2 构建项目集规范族闭包closure与转移goto的代码实现lr1_table_gen.py的核心是closure(I)和goto(I, X)两个函数def closure(I): J I.copy() changed True while changed: changed False for item in list(J): # item: (A - alpha • beta, a) if item.dot_pos len(item.beta): # 点不在末尾 B item.beta[item.dot_pos] # B 是 beta 中点后的第一个符号 if B in grammar.nonterminals: # 对每个 B - gamma 产生式添加 (B - •gamma, b) for b in compute_first_of_suffix(item.beta[item.dot_pos1:] [item.lookahead]): new_item LR1Item(B, [•] grammar.productions[B][0].rhs, b) if new_item not in J: J.add(new_item) changed True return J def goto(I, X): J set() for item in I: if item.dot_pos len(item.beta) and item.beta[item.dot_pos] X: # 将点右移一位 new_rhs item.alpha [X] item.beta[item.dot_pos1:] new_item LR1Item(item.A, new_rhs, item.lookahead) J.add(new_item) return closure(J)参数说明item.beta[item.dot_pos]是点后的符号Xcompute_first_of_suffix()计算beta[item.dot_pos1:] [item.lookahead]的 FIRST 集用于确定新项目的向前看符号closure()必须迭代直到无新项目加入否则状态不完整goto(I, X)返回的是闭包后的集合不是原始转移结果。4.3 action/goto 表生成为什么状态 4 的action[4, ] s5而不是r2lr1_table_gen.py最终输出action.csv和goto.csv。action[i, a]的取值逻辑是若goto(I_i, a) I_j且a是终结符 →action[i, a] s j移进若I_i包含项目A → α•, a且a在FOLLOW(A)中 →action[i, a] r k归约k 是产生式编号若I_i包含E → E•, $→action[i, $] acc接受。# 生成 action 表的关键判断 for i, I_i in enumerate(canonical_collection): for a in terminals: # 终结符集合 J goto(I_i, a) if J in canonical_collection: j canonical_collection.index(J) action[i][a] fs{j} # 移进 for item in I_i: if item.dot_pos len(item.beta) and item.A ! E: # 归约项目且非开始符号 for b in follow_set[item.A]: if b in terminals and action[i][b] : action[i][b] fr{prod_index[item.A, item.beta]} # 归约避坑点item.A ! E是为了排除E → E•接受项目它只在a $时生效单独处理为acc。5. 避坑指南词法、LL(1)、LR(1) 三大模块的 5 个血泪现场编译原理实验的坑往往藏在“看起来应该对”的细节里。以下是 ZIP 包使用者高频踩中的 5 个真实问题按模块归类每条给出现象、根因与可立即执行的修复方案。5.1 词法分析器123abc被识别为NUM而非ID但123单独出现时正常现象输入int x 123abc;lexer 输出(KEYWORD,int) (ID,x) (ASSIGN,) (NUM,123) (ID,abc) (SEMI,;)但期望(ID,123abc)。原因正则[0-9]排在[a-zA-Z_][a-zA-Z0-9_]*前面导致123被优先匹配剩余abc再匹配 ID。解决严格按优先级重排 PATTERNS 数组将 ID 正则置于数字正则之前。ZIP 包中lexer.java的默认顺序已是正确的检查你是否误删或移动了行。5.2 LL(1) 分析器parseStmt()方法无限递归栈溢出现象输入if (x 0) y 1;程序抛出StackOverflowError。原因Stmt → IfStmt | AssignStmt的预测表中M[Stmt, if]和M[Stmt, id]均指向IfStmt因IfStmt → if ( Expr ) Stmt的FIRST包含if而AssignStmt → id Expr ;的FIRST包含id但若IfStmt的产生式写成IfStmt → if ( Expr ) Stmt且Stmt可推导ε则FOLLOW(Stmt)会包含)导致M[Stmt, )]也指向IfStmt引发左递归。解决检查IfStmt产生式右部是否含Stmt且Stmt的FOLLOW与FIRST有交集。强制改写文法IfStmt → if ( Expr ) Stmt ElsePartElsePart → else Stmt | ε确保Stmt不直接左递归。5.3 LL(1) 预测表M[Expr, ]为空但文法明确有Expr → Expr Term现象buildParseTable()运行后M[Expr][]为null导致输入时抛出NullPointerException。原因FIRST(Expr Term) FIRST(Expr)而FIRST(Expr)若含ε则需检查FOLLOW(Expr)是否含。但FOLLOW(Expr)通常不含是Expr的内部符号非其后续符号。解决该产生式本身就不该出现在 LL(1) 文法中。必须提取左公因子Expr → Term ExprExpr → Term Expr | ε。ZIP 包中grammar.txt应采用改写后文法勿直接抄教材未改写版本。5.4 LR(1) 项目集closure()函数死循环CPU 占用 100%现象运行lr1_table_gen.py进程卡住top显示 Python 进程 CPU 100%。原因closure()中new_item的__hash__或__eq__未正确实现导致J.add(new_item)无法去重同一项目反复加入。解决检查LR1Item类是否重写了__eq__和__hash__且两者逻辑一致。例如def __eq__(self, other): return (self.A other.A and self.rhs other.rhs and self.dot_pos other.dot_pos and self.lookahead other.lookahead) def __hash__(self): return hash((self.A, tuple(self.rhs), self.dot_pos, self.lookahead))5.5 LR(1) 归约冲突action[3, *] s4/r2表生成失败现象lr1_table_gen.py报错Shift-Reduce Conflict at state 3 on symbol *。原因状态 3 同时包含移进项目T → T•*F, $和归约项目E → T•, *因*∈FOLLOW(E)。这表明文法存在固有歧义如E → E E | E * E未加优先级。解决不修改算法而修改文法。引入运算符优先级E → E T | TT → T * F | FF → id | ( E )。ZIP 包中lr1_grammar.txt应采用此无歧义版本冲突自然消失。6. 实验验证与进阶技巧用三步法把 ZIP 包变成你的“编译原理后悔药”ZIP 包的价值不在于它能跑通而在于它能让你随时回退、对比、验证每一个推导步骤。我带过 7 届编译原理实验课学生最常问“我的 LL(1) 表和答案不一样是哪里错了”——这时不要重写代码用以下三步法定位6.1 词法分析器验证用test_lex.sh生成 token 序列比对ZIP 包中通常含test/目录内有test.c示例源码。运行# 编译并运行词法分析器 javac lexer.java java lexer test/test.c test/lexer_out.txt # 人工手写预期 token按教材 P72 表 3.4 格式 # KEYWORD int # ID main # LPAREN ( # RPAREN ) # LBRACE { # KEYWORD return # NUM 0 # SEMI ; # RBRACE }用diff test/lexer_out.txt test/expected_tokens.txt比对。差异即 bug 位置若main被识别为ID但int被识别为ID说明关键字正则未生效检查PATTERNS数组顺序。6.2 LL(1) 预测表验证导出 CSV 并用 Excel 筛选空单元格ll1_table_gen.java通常含exportTableToCSV()方法。运行后得到parse_table.csv用 Excel 打开筛选Column A非终结符为Expr查看Column B终结符为、*、id、(的行空单元格即缺失项若Expr/为空说明FIRST(Expr Term)未正确计算回溯first_of()函数。6.3 LR(1) 状态机可视化用 Graphviz 画出项目集规范族ZIP 包中若有dot_generator.py运行python dot_generator.py states.dot dot -Tpng states.dot -o lr1_states.png生成的状态图中每个节点是状态编号如I0,I1边标X表示goto(I_i, X) I_j。重点检查I0是否含E → •E, $起始项目所有I_i的goto边是否覆盖全部符号accept状态含E → E•, $是否唯一且可达。我的习惯每次修改文法后必重跑dot_generator.py把新旧lr1_states.png并排放在屏幕两侧。状态数突增说明引入了冗余分支某个I_i突然消失说明closure()逻辑有缺陷。这张图就是你的“状态机后悔药”——它不撒谎只反映你手算的每一步。最后说一句实在话编译原理实验不是为了让你写出工业级编译器而是训练一种对形式系统零容忍的思维肌肉。当你能盯着FIRST(E) {, ε}这行字脑中自动浮现出 NFA 状态、DFA 转移、预测表填法、LR 项目集演化时你就真正跨过了那道门槛。这个 ZIP 包里的每一行代码都是前人把这种思维刻进键盘的痕迹。希望帮到你。本文还有配套的精品资源点击获取

相关新闻

电商评论情感分析实战:爬虫与LSTM模型完整链路解析

电商评论情感分析实战:爬虫与LSTM模型完整链路解析

简介:面向计算机相关专业学生的电商评论情感分析Python源码项目,基于深度学习LSTM算法实现,核心功能为爬取京东商城用户评论并完成情感极性分类,可作为毕业设计、课程设计或期末大作业的完整参考,也适合有Python基础、…

2026/10/13 20:11:41 阅读更多 →
OpenSpiel 状态方法 is_terminal 详解:判定游戏结束的 API 与源码实现

OpenSpiel 状态方法 is_terminal 详解:判定游戏结束的 API 与源码实现

人工智能强化学习深度学习 【免费下载链接】open_spiel OpenSpiel is a collection of environments and algorithms for research in general reinforcement learning and search/planning in games. 项目地址: https://gitcode.com/gh_mirrors/op/open_spiel 点击…

2026/10/12 15:27:41 阅读更多 →
Access 2021 数据库程序实战:从表设计到VBA自动化与部署

Access 2021 数据库程序实战:从表设计到VBA自动化与部署

简介:面向需要安装和使用 Access 2021 数据库程序的用户,这份资源包提供了完整的六十四位安装文件与配套辅助材料。其中包含解压密码说明、安装必看要点以及在线咨询通道,能有效解决获取安装包和初始化配置时的常见问题。资源内共五个文件&am…

2026/10/12 15:27:41 阅读更多 →

最新新闻

jQuery Mobile按钮组件详解:从增强机制到实战踩坑

jQuery Mobile按钮组件详解:从增强机制到实战踩坑

如果你手里还在维护 jQuery Mobile 项目&#xff0c;一定对它的按钮组件印象深刻。这个框架版本不算新了&#xff0c;但按钮这个基础控件的设计思路&#xff0c;放在今天看依然有些“超前”&#xff1a;它把普通的<a>、<input>、<button>标签重新包装&#x…

2026/10/13 20:12:08 阅读更多 →
Claude Code 终端 AI 编程助手速查:安装、权限、工作流与避坑指南

Claude Code 终端 AI 编程助手速查:安装、权限、工作流与避坑指南

1. 开工之前&#xff1a;摸清 Claude Code 的运作逻辑再上手1.1 终端里的 AI 结对编程搭档&#xff0c;到底能干什么先抛开那些花哨的宣传语&#xff0c;直接说我的真实感受&#xff1a;Claude Code 就是一个住在终端里的 AI 结对编程搭档。它不像传统 IDE 插件那样只负责补全代…

2026/10/13 20:12:08 阅读更多 →
博士求职年龄放宽至45岁:中年科研人员的机遇与准备策略

博士求职年龄放宽至45岁:中年科研人员的机遇与准备策略

消息传开之后&#xff0c;我身边几个工作群几乎在同一时间炸开了锅。一位在企业里做技术带团队的老朋友&#xff0c;博士毕业快十年&#xff0c;早就把回高校的想法抛到脑后&#xff0c;最近却开始四处打听哪里有合适的招聘信息&#xff1b;另一位在某个公司做研发管理、今年刚…

2026/10/13 20:12:08 阅读更多 →
tidyr数据整理核心:从混乱到整洁数据的七步实战

tidyr数据整理核心:从混乱到整洁数据的七步实战

1. 为什么今天还在认真学 tidyr&#xff1f;——不是为了写代码&#xff0c;而是为了把数据“理清楚”你有没有过这种经历&#xff1a;拿到一份Excel表格&#xff0c;列名是“客户ID_2023_Q3”“销售额_含税_新口径”“备注_临时_勿删”&#xff0c;打开R读进来&#xff0c;str…

2026/10/13 20:12:08 阅读更多 →
手写一个支持多目录挂载的 MCP Server:动态工作区路径切换实战

手写一个支持多目录挂载的 MCP Server:动态工作区路径切换实战

在多仓库协同或前后端分离的项目结构里&#xff0c;让大模型 Agent 自动分析代码时最常踩的坑&#xff0c;就是工作区目录的频繁切换。官方原生的 MCP&#xff08;Model Context Protocol&#xff09;本地服务端大多只在启动参数中注入一个工作区根路径。当 Agent 正在处理前端…

2026/10/13 20:12:08 阅读更多 →
三强版 Codex 一键部署包,本地桌面 AI 自动化全流程实操

三强版 Codex 一键部署包,本地桌面 AI 自动化全流程实操

&#x1f50d;前言 本文介绍 Codex Harness 一键安装包的部署方案&#xff0c;无需解压&#xff0c;也无需繁琐的环境配置&#xff0c;新手也能快速上手。该方案同时支持 Windows 与 macOS 双平台&#xff0c;跟随向导几步即可完成安装、登录与模型密钥配置。文中完整演示了技…

2026/10/13 20:11:08 阅读更多 →

日新闻

物联网系统集成避坑指南:从选型到验收的关键要点

物联网系统集成避坑指南:从选型到验收的关键要点

做了这么多年物联网系统集成的项目&#xff0c;我最大的感受是&#xff0c;大部分坑不是出在技术前沿&#xff0c;而是出在一些看起来很平常的地方。设备选了便宜的、协议没问清楚、现场没摸透、验收标准写得含糊——这些细枝末节&#xff0c;最后都会变成延期、超支和扯皮的大…

2026/10/13 0:00:57 阅读更多 →
ESP32舵机控制全攻略:从PWM原理到高级玩法与常见故障排查

ESP32舵机控制全攻略:从PWM原理到高级玩法与常见故障排查

如果你玩ESP32有一阵子了&#xff0c;很难不碰到舵机控制这道坎。做智能小车要转方向&#xff0c;做机械臂要抬关节&#xff0c;做云台要偏航俯仰&#xff0c;背后都是同一个东西在干活&#xff1a;舵机。而我见过太多人卡在“代码能编译、舵机就是不听话”这个阶段&#xff0c…

2026/10/13 0:00:57 阅读更多 →
CAN总线原理与STM32实战:抗干扰、仲裁、错误处理全解析

CAN总线原理与STM32实战:抗干扰、仲裁、错误处理全解析

1. 为什么CAN总线至今仍是工业现场的“硬通货”&#xff1f;——从汽车底盘到智能温室的真实需求你有没有拆过一辆老款燃油车的中控台&#xff1f;或者调试过某高校实验室里那台跑着Modbus协议却频频丢帧的PLC控制柜&#xff1f;又或者&#xff0c;在某个农业物联网项目里&…

2026/10/13 0:00:57 阅读更多 →

周新闻

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

简介&#xff1a;基于 ARIMA、LSTM、Transformer 等模型的流感时间序列预测 Python 源码&#xff0c;面向计算机相关专业课程设计与期末大作业学生&#xff0c;以及项目实战学习者。内容覆盖预处理、平稳性检验、定阶、残差分析、多模型对比预测的完整时序建模流程&#xff0c;…

2026/10/13 2:54:56 阅读更多 →
影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程&#xff1a;键盘模拟输入实战——输入文本与模拟按键的区别 做影刀RPA自动化&#xff0c;十个新手有八个栽在"往输入框里填东西"这件事上&#xff1a;要么填不进去&#xff0c;要么填了一半&#xff0c;要么直接把原来内容追加在后面。这背后的根因&…

2026/10/13 16:22:04 阅读更多 →
影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程&#xff1a;阅文起点小说数据采集实战——书籍信息与章节内容 1. 认识影刀&#xff1a;什么场景该用RPA采小说数据 起点中文网的页面结构相对稳定——分类榜单、书籍详情、章节内容三块独立页面&#xff0c;跳转链路清晰。这种场景非常适合影刀自动化&#x…

2026/10/13 1:58:08 阅读更多 →

月新闻

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/12 21:05:09 阅读更多 →
Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/13 14:57:39 阅读更多 →
黑夜航拍船只数据集训练YOLOV5模型全流程解析

黑夜航拍船只数据集训练YOLOV5模型全流程解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/12 18:11:17 阅读更多 →