SQL注入手工测试实战:从报错注入到数据获取

1. 项目概述:这不是“学个注入”,而是重建对Web数据交互的信任感

“2020小迪培训(第12天 WEB 漏洞--SQL 注入之简要SQL注入)”——这个标题乍看像一段课程日志,但拆开来看,它其实是一把钥匙,一把能打开Web安全底层逻辑的钥匙。我带过不少刚入门的安全学习者,他们第一次听到“SQL注入”时,常误以为这只是“在登录框里输'or 1=1--”这种魔术式操作;等真去复现、调试、绕过WAF时,才发现自己连MySQL的报错机制、PHP的mysql_real_escape_string为何失效、甚至union select为什么必须匹配列数都讲不清楚。这门课之所以叫“简要SQL注入”,恰恰是因为它不堆砌工具、不炫技盲打,而是从最朴素的请求-响应链条出发,逼你亲手把数据库当“人”来对话:你输入的每个字符,服务器怎么拼、怎么执行、怎么返回错误——每一步都暴露在HTTP明文之下。它适合三类人:一是刚写完第一个PHP留言板、正为“为什么用户注册后数据库多了一条乱码记录”发愁的开发者;二是考前突击、想搞懂CTF里sqlmap -v 3输出里那堆[INFO] testing 'MySQL > 5.0.11 AND time-based blind到底在测什么的备考生;三是运维同事,每天看Nginx日志里一堆/login.php?user=admin' and sleep(5)--却不知该封IP还是调规则的实战派。核心关键词就三个:SQL注入、Web漏洞、手工测试——它们不是孤立术语,而是一条因果链:Web应用未过滤用户输入 → 数据库引擎误将恶意字符串当SQL指令执行 → 攻击者绕过身份验证、窃取敏感数据、甚至写入Webshell。这不是黑客电影里的炫技,而是真实世界里,某次忘记对$_GET['id']做intval()就导致整张用户表被拖库的日常。

2. 内容整体设计与思路拆解:为什么“简要”反而最难教?

2.1 课程定位:拒绝“工具依赖症”,回归数据流本质

很多培训一上来就教sqlmap --dbs,结果学员能跑出数据库名,却解释不了为什么加--batch参数后information_schema.tables表名突然变全大写。而本课的“简要”,是刻意做减法:全程禁用自动化工具,只用浏览器地址栏、Burp Suite的Repeater模块、以及一个干净的MySQL命令行。设计逻辑很直白——SQL注入的本质,是用户可控输入被拼接到SQL语句中并被执行。那么教学就必须卡死在这条链路上:前端HTML表单 → 后端PHP接收变量 → 字符串拼接SQL → MySQL解析执行 → 返回HTTP响应。我们不跳过任何一环,比如专门花15分钟演示echo "SELECT * FROM users WHERE id = ".$_GET['id'];在浏览器里直接输出的原始SQL长什么样,再对比var_dump($_GET['id'])看传入的是字符串还是数字。这种“笨办法”看似低效,实则堵死了所有模糊地带:当学员亲眼看到id=1' and 1=1--拼出来变成SELECT * FROM users WHERE id = 1' and 1=1--,而MySQL报错You have an error in your SQL syntax时,他立刻明白——问题不在“攻击有多厉害”,而在“拼接有多粗糙”。

2.2 技术选型:为什么用MySQL+PHP而非其他组合?

课程锁定MySQL 5.7 + PHP 7.4环境,绝非随意。先说MySQL:它的报错信息极其“坦诚”,ERROR 1064 (42000): You have an error in your SQL syntax; ... near 'xxx' at line 1会直接告诉你语法错在哪,这对初学者理解“注入点位置”至关重要。换成PostgreSQL,报错默认只显示ERROR: syntax error at or near "xxx",少了near后面的上下文,新手根本找不到闭合单引号该加在哪。再说PHP:mysql_*函数虽已废弃,但课程用mysqli扩展,特意保留mysqli_query($conn, $sql)这种原始拼接写法,就是为了暴露风险。如果用Laravel的Eloquent,User::where('id', $_GET['id'])->first()背后是预编译,学员永远看不到SQL如何被污染。我们甚至故意部署一个phpinfo()页面,让学员自己查magic_quotes_gpc是否开启——这个2015年就废弃的配置,在某些老旧政企系统里仍阴魂不散,而课程要求学员手动php.ini里关掉它,再对比开关前后' or 1=1--的效果差异。这种“自找麻烦”的设计,是为了让学员建立一个肌肉记忆:任何Web应用,只要存在字符串拼接SQL,且未使用参数化查询,就是潜在靶子。

2.3 教学节奏:从“报错注入”切入,避开WAF干扰区

课程不按“联合注入→报错注入→布尔盲注→时间盲注”线性推进,而是第一天就直奔extractvalue()报错注入。原因很现实:联合注入需要猜列数、猜字段名,新手常卡在UNION SELECT 1,2,3--返回空页面就放弃;而报错注入只要一个and extractvalue(1,concat(0x7e,(select database()),0x7e)),MySQL直接把库名吐在报错里。我们用Burp抓包后,在Repeater里手动修改id参数,逐字节替换concat()里的内容,观察报错变化。比如把database()换成(select table_name from information_schema.tables where table_schema=database() limit 0,1),报错就变成XPATH syntax error: '~users~'——学员瞬间理解:原来information_schema不是黑客发明的,而是MySQL自带的“数据库地图”。这种即时反馈极大降低挫败感。至于WAF,课程明确告知:“别碰云WAF或360网站卫士,它们会拦截extractvalue关键字”。我们用一个极简的自定义WAF规则模拟:if (preg_match("/extractvalue|updatexml/i", $input)) die("attack detected");,然后教学员用EXTRacTVALue大小写混淆绕过。目的不是教绕过技巧,而是让学员意识到:防御的本质是规则匹配,而攻击的本质是寻找规则盲区。

3. 核心细节解析与实操要点:手工注入的“呼吸感”在哪?

3.1 注入点识别:不是找URL,是找“数据流向的断点”

很多人以为注入点就是URL里带?id=的参数,这是巨大误区。课程第一练,我们给一个真实的登录接口:POST /login.php,Body为username=admin&password=123456。学员用Burp抓包后,发现username参数改admin'--没反应,password改123456'--却返回“密码错误”。这说明后端SQL是SELECT * FROM users WHERE username='admin' AND password='123456',只有password字段参与了字符串拼接。我们进一步测试password=123456' and 1=1--,返回“登录成功”,而password=123456' and 1=2--返回“密码错误”——这就是典型的布尔盲注起点。关键细节在于:必须区分“报错注入”和“布尔盲注”的触发条件。前者依赖数据库报错回显,后者依赖应用逻辑差异(如登录成功/失败、页面有无特定文字)。课程要求学员用curl -s "http://target/login.php" --data "username=admin&password=123456' and (select 1 from mysql.user limit 0,1)=1--"手动测试,而不是依赖工具。因为curl的-s参数静默输出,你得用grep "欢迎"判断是否登录成功,这个过程强迫你思考:如果页面没有“欢迎”字样,该换什么关键词?比如搜索<title>标签里的“后台管理”?这种“呼吸感”——即根据每次响应微调下一次payload——是工具永远无法替代的手工直觉。

3.2 闭合与注释:单引号、双引号、括号的“语法呼吸”

注入成败,90%取决于闭合方式。课程用一张表格强制学员记忆不同场景的闭合组合:

后端SQL模板用户输入闭合方式原理说明
WHERE id = $_GET['id']1' and 1=1--单引号闭合,--注释id = 1' and 1=1--,--后内容被忽略
WHERE name = "$_GET['name']"" and 1=1#双引号闭合,#注释name = "admin" and 1=1#",#后被MySQL忽略
WHERE status = ($_GET['status'])1) and 1=1--括号闭合,--注释status = (1) and 1=1--),多余)被注释掉

重点讲透#和--(注意--后必须有空格)的区别:MySQL中#是行注释,--(破折号+空格)才是标准注释,很多新手输--没空格,结果整个SQL崩掉。我们让学员用MySQL命令行实测:SELECT * FROM users WHERE id = 1--123;能执行,而SELECT * FROM users WHERE id = 1--123报错,因为--123被当作文本而非注释。这种细节,只有亲手敲过才会刻进肌肉记忆。更关键的是“嵌套闭合”:当遇到WHERE title LIKE '%$_GET['q']%',单纯' or 1=1--会变成LIKE '%admin' or 1=1--%',末尾的%'导致语法错误。正确解法是%' or 1=1--,让%闭合前面的'%,--注释掉后面的%'。课程称之为“语法呼吸”——你得像呼吸一样自然感知SQL语句的起承转合。

3.3 数据库指纹识别:三步确认MySQL版本与权限

手工注入不靠sqlmap -f,而靠三步精准探测:

  1. 版本探测:id=1 and substring(@@version,1,1)='5',若返回正常,则版本以5开头;再试substring(@@version,3,1)='7'确认是5.7。原理是@@version返回字符串,substring截取字符比对布尔值。
  2. 当前用户权限:id=1 and (select count(*) from mysql.user)>0,若返回正常,说明当前用户有读mysql.user权限,可提权;若报错Access denied,则权限受限,需转向information_schema。
  3. 数据库名长度:id=1 and length(database())=8,暴力遍历1-20,找到长度后,再用ascii(substr(database(),1,1))>100二分法猜字符。课程强调:不要盲目order by猜列数。我们给一个真实案例:某电商后台/product.php?id=1,order by 10返回正常,order by 11报错,学员以为有10列。但实际SQL是SELECT id,name,price,desc FROM products WHERE id=1,只有4列。order by 10之所以不报错,是因为MySQL允许order by引用不存在的列号(只要不超过max_sort_length),这纯粹是MySQL的宽容特性。正确方法是id=1 union select 1,2,3,4--,看页面是否显示1,2,3,4——这才是唯一可靠的列数验证。

4. 实操过程与核心环节实现:从“看到报错”到“拿到数据”的完整链路

4.1 环境搭建:三台虚拟机的最小闭环

课程要求学员自建环境,而非用靶场平台。具体配置:

  • 靶机(Ubuntu 18.04):安装Apache2 + PHP7.4 + MySQL5.7,部署一个极简的user_info.php:
    <?php $id = $_GET['id']; $conn = mysqli_connect("localhost","root","123456","testdb"); $sql = "SELECT * FROM users WHERE id = ".$id; // 故意不转义! $result = mysqli_query($conn, $sql); while($row = mysqli_fetch_array($result)) { echo "Name: ".$row['name']."<br>Email: ".$row['email']; } ?>
  • 攻击机(Kali Linux):预装Burp Suite Community、curl、Python3,禁用sqlmap。
  • 监控机(Windows):用Wireshark抓靶机3306端口流量,实时查看MySQL协议里发送的真实SQL。

关键步骤是让学员在监控机上看到:当浏览器访问http://靶机/user_info.php?id=1' and extractvalue(1,concat(0x7e,database(),0x7e))--时,Wireshark捕获到MySQL协议包里,query字段赫然写着SELECT * FROM users WHERE id = 1' and extractvalue(1,concat(0x7e,database(),0x7e))--。这种“所见即所得”的冲击力,远超任何理论讲解。我们甚至要求学员用tcpdump -i any port 3306 -w mysql.pcap保存抓包文件,课后用Wireshark分析packet 12里MySQL的Error Packet结构,看SQLSTATE码42000对应“语法错误”,error message字段里XPATH syntax error如何被PHP原样返回到HTTP响应体。这种深度,让学员彻底明白:注入不是魔法,而是网络协议、数据库引擎、Web服务器三者协作的必然漏洞。

4.2 报错注入实战:extractvalue与updatexml的黄金组合

课程主攻extractvalue(),因其报错信息最清晰。Payload构造分四步:

  1. 基础验证:id=1 and extractvalue(1,1),确认报错是否触发(应返回XPATH syntax error: '1')。
  2. 数据库名提取:id=1 and extractvalue(1,concat(0x7e,(select database()),0x7e)),0x7e是~的十六进制,用于分隔,避免与库名混淆。
  3. 表名提取:id=1 and extractvalue(1,concat(0x7e,(select table_name from information_schema.tables where table_schema=database() limit 0,1),0x7e)),这里limit 0,1取第一张表,information_schema.tables是MySQL元数据表,存储所有表名。
  4. 字段名提取:id=1 and extractvalue(1,concat(0x7e,(select column_name from information_schema.columns where table_name='users' limit 0,1),0x7e)),注意table_name='users'要用单引号闭合,因information_schema.columns里table_name是字符串字段。

难点在于limit偏移。课程教学员用burp intruder爆破limit {pos},1,设置pos从0到10,观察报错中~之间的内容变化。比如pos=0报错XPATH syntax error: '~users~',pos=1报错XPATH syntax error: '~password~',说明users表有password字段。我们强调:永远不要相信information_schema的table_rows字段。某次实操中,学员看到table_rows=0就放弃,结果手动select * from users发现有1000条数据——因为table_rows是估算值,innodb引擎下不准。正确做法是直接select count(*) from users。

4.3 联合注入进阶:绕过ORDER BY陷阱的实战技巧

当目标站关闭报错回显(display_errors=Off),必须切联合注入。但新手常栽在ORDER BY上。课程给出真实避坑方案:

  • 列数探测:不用order by,改用id=-1 union select 1--,若返回空页面,说明列数不对;再试id=-1 union select 1,2--,直到页面出现1和2。原理是-1确保主查询无结果,union结果直接显示。
  • 字段类型匹配:id=-1 union select 'a',2,3--,若页面显示a,2,3,说明第一列是字符串;若报错Illegal mix of collations,则第一列是数字,需改1。我们让学员用select @@collation_database查靶机默认校对集,再用convert('a' using utf8mb4)强制转码。
  • 数据导出:id=-1 union select 1,group_concat(username,0x3a,password),3 from users--,0x3a是:的十六进制,group_concat将所有用户名密码拼成一行。重点讲group_concat的SEPARATOR参数:group_concat(username separator '|')可自定义分隔符,避免用户名含逗号导致解析混乱。

5. 常见问题与排查技巧实录:那些文档里不会写的“血泪经验”

5.1 典型问题速查表

问题现象排查思路解决方案经验备注
id=1'返回500错误,但id=1正常检查单引号是否被PHP自动转义在php.ini中确认magic_quotes_gpc=Off,或用stripslashes()处理2020年仍有老旧系统开启此配置,务必首查
extractvalue()报错但无数据回显MySQL版本低于5.1.5,不支持extractvalue改用updatexml():id=1 and updatexml(1,concat(0x7e,(select database()),0x7e),1)updatexml在MySQL 5.1.5+可用,报错格式略有不同
union select返回空页面,无报错主查询与union列数/类型不匹配用id=-1 union select null,null,null--逐列试null,null可匹配任意类型null是万能占位符,比数字或字符串更可靠
Burp Repeater中修改参数无效请求被浏览器缓存或302重定向在Repeater中勾选Follow redirects,或在Proxy选项卡关掉Intercept后重放浏览器缓存常导致“改了没反应”的假象
information_schema查询超时目标库表过多,information_schema扫描慢改用show databases和show tables命令,它们更快show命令是MySQL内置,不走information_schema表

5.2 独家避坑技巧:来自真实渗透现场的教训

技巧一:用sleep()验证布尔盲注,但别信“秒级响应”
某次渗透中,学员用id=1 and sleep(5)测试,发现响应时间仅1.2秒,断定“没效果”。我让他用time curl -s "http://target/user.php?id=1 and sleep(5)"实测,结果real 5.03s。真相是:PHP的max_execution_time=30限制了脚本总时长,但sleep()是系统调用,不受PHP超时影响。而浏览器显示的“1.2秒”是TCP连接建立+SSL握手时间,真正的SQL执行耗时被埋在响应体里。正确姿势:永远用time curl或Burp的Response Time列看真实延迟。

技巧二:group_concat截断?不是数据丢了,是group_concat_max_len限制了
学员导出用户表时,发现只拿到前100个用户名。show variables like 'group_concat_max_len';查出默认值1024,意味着最多拼1024字符。解决方案:SET SESSION group_concat_max_len=1000000;临时提升,或直接select concat_ws('|',username,password) from users用concat_ws替代。

技巧三:WAF拦截union select?试试unIon SeLect大小写+空格混淆
某政务网站WAF规则是/union\s+select/i,学员输union select被拦,改unIon SeLect通过。但更狠的是id=1/**/union/**/select/**/1,2,3--,/**/是MySQL注释符,等价于空格,且多数WAF规则不覆盖注释。课程强调:绕过WAF不是目的,而是理解其规则边界的实验。

技巧四:load_file()读不到/etc/passwd?检查MySQL用户文件权限
select load_file('/etc/passwd')返回NULL,不一定是路径错。用select @@secure_file_priv查MySQL允许读取的目录,若返回/var/lib/mysql-files/,则只能读该目录下文件。这是MySQL 5.7+的安全加固,默认禁用任意文件读取。

6. 防御实践与代码加固:从“怎么破”到“怎么防”的思维跃迁

6.1 开发者必改的三行代码

课程最后半小时,不讲攻击,只讲防御。给出PHP开发者的“救命三行”:

// 1. 绝对禁用字符串拼接SQL // ❌ 错误:$sql = "SELECT * FROM users WHERE id = ".$_GET['id']; // 2. 强制参数化查询(PDO) $stmt = $pdo->prepare("SELECT * FROM users WHERE id = ?"); $stmt->execute([$_GET['id']]); $result = $stmt->fetchAll(); // 3. 输入类型强校验 $id = filter_input(INPUT_GET, 'id', FILTER_SANITIZE_NUMBER_INT); if (!$id || $id <= 0) die("Invalid ID");

重点解释FILTER_SANITIZE_NUMBER_INT:它会移除所有非数字字符,id=1' or 1=1--变成1,彻底杜绝注入。我们对比FILTER_VALIDATE_INT(只验证不清理)和FILTER_SANITIZE_NUMBER_INT(清理后返回),用var_dump(filter_var("1abc2", FILTER_SANITIZE_NUMBER_INT))实测输出string(2) "12",证明其清理能力。课程强调:防御不是加一层WAF,而是让恶意输入在进入SQL前就变成无害数字。

6.2 运维侧加固:MySQL配置的五个致命开关

针对运维人员,列出必须检查的MySQL配置:

  1. secure_file_priv=/var/lib/mysql-files/:限制load_file()读取路径,设为NULL则完全禁用。
  2. sql_mode=STRICT_TRANS_TABLES,NO_ZERO_DATE,NO_ZERO_IN_DATE,ERROR_FOR_DIVISION_BY_ZERO:开启严格模式,让非法数据插入直接报错而非静默截断。
  3. local_infile=OFF:禁用LOAD DATA LOCAL INFILE,防止文件上传。
  4. skip-show-database:禁止非super权限用户执行show databases。
  5. default_password_lifetime=90:强制密码90天更换,降低凭证泄露风险。

我们让学员用mysql -u root -p -e "SHOW VARIABLES LIKE 'secure_file_priv';"验证配置,并手动生成my.cnf加固模板。课程结语只有一句:“你今天手工注入成功的每一个payload,都应该成为明天代码审查清单上的一条红线。”

相关新闻

本体驱动开发:为AI原生应用构建可掌控的语义契约层

本体驱动开发:为AI原生应用构建可掌控的语义契约层

做AI原生应用开发这几年&#xff0c;我最大的感触是&#xff1a;大模型让“理解”变得廉价&#xff0c;却让“协作”变得昂贵。单次问答的demo人人都能做&#xff0c;但一旦你要让AI替你长期管一批结构化的业务资产——比如笔记、工单、设备台账——就一定会撞上同一个墙&#…

2026/10/20 5:08:59 阅读更多 →
告别监控盲区:KeyarchOS安装NRPE-3.2.1实配置指南

告别监控盲区:KeyarchOS安装NRPE-3.2.1实配置指南

告别监控盲区&#xff01;KeyarchOS安装nrpe-3.2.1-8&#xff0c;远程主机指标采集开箱即用监控盲区这四个字&#xff0c;伺候过大规模服务器的同学应该都懂。你辛辛苦苦把监控平台搭起来&#xff0c;CPU、内存、磁盘看个一目了然&#xff0c;偏偏到了某些非标准部署、临时扩容…

2026/10/20 5:07:58 阅读更多 →
高校专业建设管理系统开发实战:从业务建模到数据库设计

高校专业建设管理系统开发实战:从业务建模到数据库设计

高校专业建设管理系统&#xff0c;这个标题我第一次看到时&#xff0c;第一反应是&#xff1a;这不就是个典型的后台管理系统吗&#xff1f;等真正接手需求&#xff0c;才发现"专业建设"这四个字背后&#xff0c;是高校教务里最繁琐、最吃业务理解的一块。所谓专业建…

2026/10/20 5:07:58 阅读更多 →

最新新闻

小白程序员必看:如何成为高薪AI全栈工程师?

小白程序员必看:如何成为高薪AI全栈工程师?

本文介绍了AI全栈工程师这一新兴高薪岗位&#xff0c;解释了其概念、所需技能以及为何如此火爆。文章指出&#xff0c;AI全栈工程师能够使用AI编程工具独立完成从界面到上线的整个系统开发&#xff0c;降低了行业门槛&#xff0c;提升了个人不可替代性。文章还澄清了关于AI全栈…

2026/10/20 5:42:15 阅读更多 →
拆解六款开源RAG产品后,我逆向出一套自研蓝图

拆解六款开源RAG产品后,我逆向出一套自研蓝图

1. 从六款开源RAG产品里&#xff0c;我逆向出了一套自研蓝图做RAG&#xff08;检索增强生成&#xff09;自研这件事&#xff0c;我前前后后折腾了快一年。最开始的想法很简单&#xff1a;开源方案这么多&#xff0c;随便挑一个改改就能用。结果真上手才发现&#xff0c;每个开源…

2026/10/20 5:42:15 阅读更多 →
AI辅助科研与代码:从工具选型到工作流的系统方法论

AI辅助科研与代码:从工具选型到工作流的系统方法论

1. 为什么“AI辅助科研与代码”值得认真对待这两年&#xff0c;我身边做科研和写代码的朋友&#xff0c;几乎没有人不在工作流里塞进一两个AI工具。有人用它读文献、有人用它写脚本、有人用它调参、有人用它改论文。但真正让我觉得值得写一篇系统总结的&#xff0c;不是“AI能做…

2026/10/20 5:42:15 阅读更多 →
从0开始学架构-28:业务高可用的保障异地多活架构

从0开始学架构-28:业务高可用的保障异地多活架构

无论是高可用计算架构,还是高可用存储架构,其本质的设计目的都是为了解决部分服务器故障的场景下,如何保证系统能够继续提供服务。但在一些极端场景下,有可能所有服务器都出现故障。例如,典型的有机房断电、机房火灾、地震、 水灾......这些极端情况会导致某个系统所有服务…

2026/10/20 5:42:15 阅读更多 →
压缩感知与图像加密混合算法:密钥控制测量矩阵的原理与Matlab实现

压缩感知与图像加密混合算法:密钥控制测量矩阵的原理与Matlab实现

很多人第一次看到“基于压缩感知的压缩加密混合算法”这个标题时&#xff0c;心里大概都会冒出同一个问题&#xff1a;压缩感知本身不就是在压缩图像吗&#xff0c;加密再单独做一层不就行了&#xff0c;为什么非要扯到一起&#xff1f;我一开始也是这个想法&#xff0c;直到真…

2026/10/20 5:42:15 阅读更多 →
文件系统边界才是批量删除的隐形天花板:一次缓存清理引发的思考

文件系统边界才是批量删除的隐形天花板:一次缓存清理引发的思考

48,218 个文件&#xff0c;103 秒&#xff0c;平均每秒删掉 468 个。这个速度放在本地 SSD 上不算惊艳&#xff0c;放在机械盘安全软件钩子的业务机上&#xff0c;已经算靠谱了。真正有意思的是这次清理引发的一场争论&#xff1a;团队里有人坚持说提示词写得不够好&#xff0c…

2026/10/20 5:41:14 阅读更多 →

日新闻

CLRC663芯片Pin-to-Pin替代实战:从评估到量产全记录

CLRC663芯片Pin-to-Pin替代实战:从评估到量产全记录

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

2026/10/20 1:01:30 阅读更多 →
ESP32舵机控制指南:原理、多路驱动与避坑实战

ESP32舵机控制指南:原理、多路驱动与避坑实战

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

2026/10/20 1:01:30 阅读更多 →
位移法实现一阶低通滤波:单片机ADC采样降噪实战

位移法实现一阶低通滤波:单片机ADC采样降噪实战

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

2026/10/20 1:01:30 阅读更多 →

周新闻

基于GMM的语音识别系统原理与MATLAB实现详解

基于GMM的语音识别系统原理与MATLAB实现详解

说到基于高斯混合模型&#xff08;GMM&#xff09;的语音识别系统&#xff0c;很多人第一反应就是一堆数学公式&#xff0c;觉得门槛很高。但如果你真的在MATLAB里把它落地跑通&#xff0c;会发现核心其实就是三件事&#xff1a;把声音变成特征向量&#xff0c;用GMM给每个类别…

2026/10/19 10:02:04 阅读更多 →
数字图像处理入门:反白、灰度化、调色板修改与导出txt实践

数字图像处理入门:反白、灰度化、调色板修改与导出txt实践

数字图像处理这四个字听起来挺唬人&#xff0c;但落到具体操作上&#xff0c;无非就是让计算机按你的想法“摆弄”像素。我在一个模拟项目X里用了一套特别经典的基础处理流程&#xff1a;对图像做反白、改调色板、彩色转灰度&#xff0c;最后把像素数据导出成txt文件。单看每一…

2026/10/19 17:32:41 阅读更多 →
机器人大脑技术盘点:具身智能的感知、决策与数据闭环

机器人大脑技术盘点:具身智能的感知、决策与数据闭环

如果你的信息流最近也天天刷到“机器人大脑”这个词&#xff0c;你会发现一个很有意思的现象&#xff1a;每个人说的“大脑”根本不是同一个东西。有人指的是大语言模型&#xff0c;有人指的是运动控制系统&#xff0c;还有人指的是能理解物理世界的端到端模型。在2026年这个时…

2026/10/20 2:50:50 阅读更多 →

月新闻

我发现了一个新思路:用 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/19 2:54:50 阅读更多 →
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/19 9:10:22 阅读更多 →
黑夜航拍船只数据集训练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/18 12:16:16 阅读更多 →