ARTICLE DETAIL

资讯详情

深耕编程入门与网站建设的一线实战洞察。

嵌入式开发入门:Arduino与ESP32踩坑实录及智能小车实战

嵌入式开发入门:Arduino与ESP32踩坑实录及智能小车实战 第一次把Arduino Uno插上电脑我盯着串口监视器里的空白等了十分钟以为板子坏了。后来才知道那个空白是无数嵌入式新手的第一道坎而跨过这道坎的过程几乎涵盖了嵌入式开发最核心的思维方式环境、工具、硬件、通信、调试。这篇博文不打算按官方教程的口吻来写。我把它当成一次“踩坑总结实操复盘”来整理覆盖从Arduino到底是什么、怎么把ESP32/ESP8266的开发环境装明白到串口监视器、舵机控制、智能小车这类实际项目的完整落地路径。无论你手里的板子是Uno还是ESP32甚至暂时没板子只想在Wokwi上仿真这篇内容都能直接用上。1. Arduino嵌入式开发到底是什么小白最容易误会的三件事1.1 Arduino不是玩具是一套完整的嵌入式开发工具链很多人把Arduino当成“电子积木”觉得它就是给中小学生玩的。这个理解只对了一半。Arduino真正的价值是它把嵌入式开发里最磨人的部分——硬件初始化、编译上传、串口通信——全部封装成了几行代码就能搞定的接口。你不需要一上来就啃芯片手册不需要自己搭烧录器甚至不需要理解寄存器怎么配置就能让一个LED按照你的意愿闪烁。但封装不意味着没有深度。Arduino底层的硬件还是AVR或ARM芯片它一样有中断、定时器、PWM、ADC这些嵌入式开发的经典概念。你可以在Arduino上做纯应用层的逻辑也可以一步步往下挖直到直接操作寄存器、写驱动、甚至给UNO重新烧录引导程序。这也是为什么它既能进小学课堂也能出现在大学嵌入式课程的实验台上。嵌入式开发这个方向的入门难点从来不是某个具体语法而是“软件和硬件交叉”的思维方式。你在电脑上写的代码不再是跑在一个操作系统里的程序而是要直接和引脚电平、时序、电压、电流打交道。Arduino的价值在于它用最简单的方式把这种交叉思维教给你而且容错率很高——接错线、写错代码最坏结果也就是板子不工作很少会烧东西。1.2 应用层开发算不算嵌入式这个争论到底在争什么“应用层开发是不是嵌入式”是社区里常年吵架的话题。有人说我只用Arduino写逻辑调API这不就是高级一点的C语言开发吗也有人说嵌入式开发就应该是裸机、寄存器、中断向量表、内存映射否则都是“伪嵌入式”。我的观点是这样的嵌入式开发覆盖的链路很长从芯片选型、原理图设计、PCB Layout到Bootloader、底层驱动、操作系统移植再到中间件和应用逻辑每一层都是嵌入式。Arduino让你做的是最顶层的应用逻辑但你不能因为它帮你封装了底层就说它不是嵌入式开发。真实的工业项目里同样有人用STM32写应用层有人用嵌入式Linux做Qt界面这些都是嵌入式开发的组成部分。“应用层开发是不是嵌入式”这个问题放在职业规划里看更有意义。如果你未来想往嵌入式Linux驱动开发方向走那Arduino只是帮你建立硬件感觉的跳板真正的主战场是设备树、内核模块、字符设备驱动那些内容。如果你只想快速做产品原型、搞硬件DIY、做物联网设备那Arduino这条路可以走得很远。两条路没有高下之分只有目标不同。1.3 选对开发板Uno、ESP8266、ESP32到底怎么选很多新手一上来就在Uno和ESP32之间纠结。我直接给结论先看你的项目需不需要联网再看你对性能的要求。开发板主频Flash典型特性适合场景参考价格Arduino Uno16MHz32KB5V逻辑、海量教程、外设丰富入门教学、舵机控制、传感器实验30-50元Arduino Nano16MHz32KB体积小、可插面包板小型DIY、便携项目15-30元ESP8266160MHz4MB自带WiFi、价格极低IoT数据上报、智能家居10-20元ESP32240MHz4-16MBWiFi蓝牙、性能强、ADC/DAC丰富本地AI、音视频、复杂物联网20-40元Uno的定位是“学习曲线最平滑”。它的5V逻辑电平让很多传感器模块可以直接对接不用考虑电平转换。但它的短板也很明显32KB的Flash、2KB的RAM跑不了太复杂的程序也没有WiFi。ESP8266的出现几乎把入门板的价格和性能天花板拉高了一个档次10块钱左右就能跑WiFi。但ESP8266只有一路ADC模拟采样能力弱而且3.3V逻辑电平和5V传感器对接时需要转换。ESP32则是目前DIY领域最均衡的选择。双核240MHz、WiFi蓝牙、支持Arduino生态跑个TFT屏幕界面、做个语音识别、挂个摄像头都没有压力。如果你预算允许我会直接建议从ESP32开始但如果你是想完全理解嵌入式底层的原理Uno的ATmega328P反而是更好的学习对象——它足够简单你能看透一切。2. 从零搭建Arduino开发环境这一篇踩坑实录够你少走两周弯路2.1 Arduino IDE 2.x和1.8.x到底选哪个版本Arduino IDE目前有两个主流大版本传统的1.8.x和新的2.x。2.x基于Eclipse Theia重构界面更现代集成了自动补全、实时调试、串口绘图器这些体验确实比1.8.x好太多。但它有个让人头疼的问题首次启动要加载一堆组件在某些网络环境下下载依赖慢得让人怀疑人生甚至直接卡在启动画面。我的建议是如果你用的是Uno/Nano这类经典板暂时又没有ESP32需求1.8.x依然是最稳妥的选择——它启动快、稳定、插件生态成熟。如果你想用2.x的新特性或者需要同时管理多块开发板那2.x值得尝试但要做好心理准备大概率会遇到下载慢、插件装不上、打开空白这类状况。IDE下载后打不开、界面空白大概率是这几个原因安装路径包含中文或空格导致配置文件读取异常首次启动需要联网下载组件网络不通卡住了电脑缺少必要的运行库尤其是老Windows系统解决办法很简单把IDE装到纯英文路径下首次启动前先挂好网络实在不行就用离线包版本。具体离线包怎么弄下一节展开讲。2.2 ESP32和ESP8266开发环境安装在线装不上就用镜像源和离线包ESP32和ESP8266要用Arduino IDE开发第一步是添加开发板管理器URL。这个操作本身只有两步打开“文件-首选项”在“附加开发板管理器网址”里填入JSON链接然后在“工具-开发板-开发板管理器”里搜索并安装。但真正的坑在第三步ESP32的官方JSON来源托管在GitHub上在国内网络环境下经常下载失败要么卡在0%要么下载到一半报错。这个问题我试过很多种解法最有效的有三个第一种换阿里巴巴的国内镜像源。JSON地址换成阿里提供的地址开发板管理器里的下载速度会快很多而且不容易断。这里要注意不同镜像源的JSON对应版本可能不完全同步安装完成后最好在开发板管理器里确认一下版本号。第二种直接下载离线包。离线包实际上是ESP32/ESP8266的完整工具链压缩包里面包含了编译器、烧录工具、核心库。比如ESP32 3.3.11的完整工具链包下载后手动解压到Arduino15目录下的packages文件夹里再配合JSON配置IDE就能识别出对应版本的ESP32开发板。具体路径在Windows下一般是C:\Users\你的用户名\AppData\Local\Arduino15\packages把解压后的esp32文件夹放进去就行。第三种混合方案。先安装一个低版本的开发板支持比如能正常下载的版本再用离线包覆盖升级到目标版本。这个方案适合那些网络实在不稳定但又想用最新版本特性的场景。我说句实话ESP32环境搭建这个环节劝退了很多人。它不是技术难度大而是网络环境导致的挫败感太强。我第一次装ESP32时反复试了三四个小时才搞定后来发现用离线包五分钟就解决了。所以如果你也卡在这一步别死磕在线下载直接找对应版本的离线包。2.3 给Uno板烧录引导程序什么时候需要应该怎么操作引导程序Bootloader是Arduino板子上电后最先运行的一段程序它的作用是等待电脑通过串口发来的程序数据然后把新程序写入Flash。官方出厂的Uno都已经烧好了引导程序正常情况下你不需要碰它。但有两种情况你必须自己烧第一板子是从某个不靠谱的渠道买的出厂时没烧引导程序插上电脑后连端口都认不到第二你写了一个把Flash写坏的底层程序或者烧录过程中断电引导程序被破坏了。给Uno烧引导程序最经典的方案是“用另一块Arduino做ISP”。你需要一块能正常工作的Arduino板比如另一块Uno或Nano按以下步骤操作打开IDE先给“作为编程器”的那块板子烧录ArduinoISP示例程序文件-示例-11.ArduinoISP按ISP引脚定义把编程器和目标板正确连接注意MISO、MOSI、SCK、RESET这四根线不能接错在IDE的“工具-编程器”里选择“Arduino as ISP”选择目标板的型号点击“烧录引导程序”整个过程大约需要一两分钟。烧录成功后目标板就会出现在电脑的串口列表里之后就可以正常通过USB上传程序了。这块我多说一句如果你手头只有一块板子千万别尝试在线擦除引导程序。我见过有人为了“试试看”把Uno的熔丝位改了结果板子直接变砖只能买USBasp之类的AVR下载器才能救回来。改熔丝位之前一定先确认自己有没有恢复手段。3. 核心外设实战串口监视器、舵机控制与String处理3.1 串口监视器显示空白或乱码问题基本都出在这四个地方串口监视器是Arduino调试的“眼睛”。你写的Serial.println打印出来的数据都得通过它来看。但几乎所有新手都会遇到串口打开后一片空白或者满屏乱码的情况这里面的原因其实很有限。第一个原因是波特率不匹配。代码里Serial.begin(9600)写了多少串口监视器右下角就得选多少。如果你代码里写的是115200监视器窗口却选了9600出来的就是乱码。这个错误很基础但架不住它容易出现而且一旦出现新手往往会忽略去检查。第二个原因是烧录程序时串口被占用。很多板子在烧录完成后会自动复位这时候如果监视器开着可能就错过了启动时的打印信息。你先关掉监视器烧录完成后再重新打开基本就能看到输出。某些ESP32开发板还会因为DTR/RTS引脚的电平问题导致串口不输出这时候可以试试把开发板上的EN引脚手动复位一下。第三个原因是TX和RX接线接反了。如果你在用USB转TTL模块连接板子A模块的TX要接B板子的RX交叉连接。接成直连的话数据就消失在空气里了。这个错误比较隐蔽因为它不会烧东西只是单纯地没数据。第四个原因比较冷门代码里根本没有Serial.begin或者串口被某个传感器的库占用了。我之前调试一个舵机项目时串口突然不输出排查了半天发现是另一个库在初始化时把串口号重置了。最后补一个实用技巧如果数据量很大你发现串口监视器滚动太快看不清就把波特率调高到115200或者在代码里加一个延时。如果希望数据可视化Arduino IDE 2.x自带串口绘图仪能把波形画出来调试超声波测距这类连续数据时特别好用。3.2 控制舵机接线不难难的是供电和抖动舵机是很多Arduino项目的第一个“执行机构”。智能小车转向、机械臂关节、摄像头云台全靠它。舵机的控制原理不复杂它有一个信号线接收PWM波PWM波的脉宽决定了舵机输出轴的角度。以SG90这类模拟舵机为例典型的PWM周期是20ms其中高电平时间在0.5ms到2.5ms之间对应0度到180度。Arduino的Servo库把这些细节全部封装好了你只需要写myservo.write(90)就能让舵机转到90度。代码长这样#include Servo.h Servo myservo; void setup() { myservo.attach(9); // 信号线接9号引脚 } void loop() { myservo.write(0); // 转到0度 delay(1000); myservo.write(180); // 转到180度 delay(1000); }代码很简单但硬件上有两个大坑。第一舵机启动瞬间电流很大。SG90空载时电流约100mA堵转时能到500mA以上而MG996R这类大舵机启动电流能达到2A甚至更高。Arduino板上那个AMS1117稳压芯片根本承受不住这么大的电流强行从5V引脚取电会导致板子反复重启舵机会出现“抽搐”的抖动现象。正确的做法是单独准备一个5V稳压模块或者电池组给舵机供电并且把电源地和Arduino的GND接到一起。第二舵机信号对时序比较敏感。如果你用delay(1000)阻塞主循环舵机控制没问题但如果同时要跑传感器扫描delay期间传感器就没法采样了。这时候要改用millis()非阻塞定时方案或者让舵机库配合定时中断工作。还有一个经验之谈舵机在不通电的时候用手去拧它的输出轴会感觉到阻力这是正常的。但如果通电后舵机嗡嗡响、发热明显、轴却不转那大概率是舵机扫齿了或者供电不足赶紧断电检查。3.3 少用String这是Arduino社区教得最贵的一课Arduino里有两种处理文本数据的方式一种是C语言原生的char数组另一种是Arduino封装好的String类。新手往往偏爱String因为它支持拼接、equals比较写起来太方便了。但String类的实现机制是动态内存分配。它会在堆上不断申请和释放内存时间长了会导致堆碎片化。在只有2KB RAM的Uno上这种现象尤其致命——你可能突然发现程序跑着跑着就没反应了Serial打印也停了。这就是典型的内存碎片化导致的堆耗尽。你可能会说我跑ESP32那么大的RAM还在乎这个吗话虽这么说但嵌入式开发的习惯是刻在骨子里的资源节省思维。工业级的嵌入式代码几乎不用动态分配因为你知道系统里每个字节的去向。个人经验是能用char数组就用char数组拼接用snprintf来格式化。比如你要输出传感器数据char buffer[64]; snprintf(buffer, sizeof(buffer), Distance: %d cm, distance); Serial.println(buffer);这个习惯一开始可能觉得麻烦但好处很快就能体会到代码更可控、性能更稳定、Flash占用也少。我自己从String转char数组之后程序异常重启的毛病几乎消失了大半。4. 实战项目复盘智能小车与超声波防撞系统4.1 Arduino智能小车的完整设计思路从硬件到代码一次讲透智能小车是Arduino项目里最经典的“综合训练场”。它同时涉及传感器输入、逻辑决策、电机驱动、供电设计几乎把嵌入式开发的几个核心环节都覆盖了。我以一辆普通的超声波避障小车为例拆解一下整体思路。硬件清单如下Arduino Uno/ESP32主控板L298N或TB6612电机驱动模块直流减速电机x2带车轮HC-SR04超声波传感器SG90舵机用来转超声波传感器电池组或锂电池建议7.4V以上5V稳压后再给板子供整车的核心逻辑是一个循环超声波测距判断前方障碍物距离如果距离大于阈值就直行小于阈值就停下来左右看选择更空旷的方向转弯。这套逻辑看起来简单但有几个细节直接决定小车跑得好不好。第一个细节是超声波传感器的布置方案。固定朝前的安装方式结构简单但只能探测正前方一个小角度区域转弯容易撞到侧面的障碍物。把传感器装到舵机上让它能左右扫描相当于给小车加了一个“转头探路”的功能。代码上通过舵机在不同角度分别测距然后比较哪个方向更开阔。第二个细节是电机PWM调速。L298N模块一般用两个引脚控制方向IN1/IN2一个引脚控制速度ENA接PWM引脚。前进时IN1高IN2低后退反过来。转向可以通过左右轮差速实现左转时右轮加速或左轮减速。PWM值的大小直接影响电机转速但要注意PWM频率Arduino默认的490Hz对有些电机来说会发出啸叫声可以用analogWriteFrequencyESP32或改TIMER分频来调整。第三个细节是电源分配。L298N模块通常可以从电机电源取电给逻辑电路供电但如果你让Arduino的5V去给传感器、舵机、电机驱动全部供电绝对撑不住。正确方案电池组直连L298N的供电端L298N自带的5V输出给Arduino供电然后Arduino再给传感器供5V舵机单独从5V稳压模块取电。每个关键模块都有独立的供电来源才不会互相干扰。来看看核心的避障代码框架#include Servo.h Servo headServo; const int trigPin 7; const int echoPin 6; const int enA 5; const int in1 8; const int in2 9; int speedValue 180; void setup() { headServo.attach(10); pinMode(trigPin, OUTPUT); pinMode(echoPin, INPUT); pinMode(enA, OUTPUT); pinMode(in1, OUTPUT); pinMode(in2, OUTPUT); } int getDistance() { digitalWrite(trigPin, LOW); delayMicroseconds(2); digitalWrite(trigPin, HIGH); delayMicroseconds(10); digitalWrite(trigPin, LOW); long duration pulseIn(echoPin, HIGH); return duration * 0.034 / 2; } void goForward() { digitalWrite(in1, HIGH); digitalWrite(in2, LOW); analogWrite(enA, speedValue); } void stopCar() { digitalWrite(in1, LOW); digitalWrite(in2, LOW); } void loop() { int distance getDistance(); if (distance 25) { headServo.write(90); goForward(); } else { stopCar(); headServo.write(45); int leftDist getDistance(); headServo.write(135); int rightDist getDistance(); headServo.write(90); if (leftDist rightDist) { // 左转逻辑 } else { // 右转逻辑 } } delay(50); }这段代码只是一个可运行的最小框架实际调试时你还要处理几个问题HC-SR04在2cm和400cm之间的测量范围低于2cm时读数是不可靠的多个传感器同时测距时会互相串扰脉冲读取pulseIn()是阻塞式的测距期间其他任务会卡住。4.2 从智能小车到超声波预警防撞系统场景迁移的思维方式智能小车里练出来的技能换一个场景就能变成完全不同的产品。我见过一个很有意思的校园项目在走廊拐角盲区安装超声波测速预警防撞系统。它的应用场景是校园走廊拐角处两侧的人看不到对方骑自行车或跑步的人很容易撞上。这个项目的方案逻辑和小车避障几乎一模一样用超声波传感器测距当检测到物体在安全距离内时触发声光报警蜂鸣器LED提醒拐角两侧的人注意。唯一的不同是小车是移动的预警系统是固定的所以供电可以用USB或者锂电池持续供着代码也简单得多void loop() { int distance getDistance(); if (distance threshold) { digitalWrite(buzzerPin, HIGH); digitalWrite(ledPin, HIGH); } else { digitalWrite(buzzerPin, LOW); digitalWrite(ledPin, LOW); } delay(100); }这个项目的价值不在于代码难度而在于你学会了“需求分析-传感器选型-逻辑实现-现场部署”的完整链路。类似的思路还可以迁移到倒车雷达、老人跌倒检测、智能垃圾桶等场景核心都是“用传感器感知环境用逻辑判断状态用执行器做出响应”。如果你是在米思齐Mixly这类图形化编程平台上做项目思路也是一样的。米思齐把Arduino的代码封装成了积木块超声波模块、蜂鸣器、RFID读卡器都有现成的积木。RFID实验说白了就是用RC522模块读卡当检测到特定卡号时触发开锁或者亮灯逻辑和上面的预警系统本质相同只是输入源从超声波换成了RFID。4.3 Wokwi仿真平台没买板子也能玩的线上实验室很多新手还没决定买哪块开发板或者板子还在快递路上就已经想动手写代码了。这种情况我强烈推荐用Wokwi仿真平台。它是一个在浏览器里运行的电子电路仿真工具直接支持Arduino Uno、ESP32、ESP8266等主流开发板还内置了面包板、LED、舵机、超声波传感器、LCD显示屏这些常用元件。Wokwi最大的优势是零成本试错。你可以先在仿真里把电路搭出来、代码调通再花真金白银买硬件。而且它天然支持代码分享链接一发给别人就能看到你的完整项目和运行效果这在远程沟通场景里非常实用。我个人的体验是Wokwi用来验证逻辑和调试代码完全够用但有两个局限第一仿真环境里没有真实的电气噪声和接触不良所以真实项目中可能出现的供电不足、信号抖动在仿真里不会出现第二它没法真正测网络通信比如ESP32连WiFi这种场景仿真只能模拟部分功能。所以我的建议是用Wokwi入门和验证逻辑但最终一定要买板子动手把真实项目跑起来。4.4 硬件调试心得那些教程里不会明说的细节做完几个项目之后我开始整理“硬件调试”这个环节的心得。软件调试有断点、有日志硬件调试很多时候靠的是经验和直觉。第一先排除供电问题再查代码。嵌入式硬件项目里至少有一半的“神秘故障”是供电问题。电机一启动单片机就重启大概率是电压跌落传感器读数飘忽不定大概率是共地没做好或者电源纹波太大。遇到问题先拿万用表量一下各路电压不要急着改代码。第二用示波器看PWM波形。舵机不转、电机速度不对与其瞎猜不如直接把信号引脚接上示波器看看波形。脉宽是不是对频率是不是预期值一眼就能看明白。没有示波器的话也可以用逻辑分析仪几十块钱的就能用。第三养成“一次只改一个变量”的调试习惯。我在调试小车时经常同时调整PWM阈值、转向时间、超声波间隔结果车越调越乱。后来强迫自己每次只改一个参数改动后跑一段固定路线记录效果效率反而高了好几倍。第四必要的时候用串口打印辅助定位。在关键节点加Serial.println观察数据是否符合预期。这个习惯看起来傻但往往是最快锁定问题的方式——尤其是在嵌入式环境的早期调试阶段。5. 常见问题速查表与进阶路线5.1 嵌入式开发高频问题速查表问题现象可能原因解决方案IDE下载后打不开/打开空白安装路径有中文/缺少运行库/首次加载卡住重装到纯英文路径检查运行库使用离线包版本开发板管理器下载ESP32卡0%网络无法访问下载源换阿里巴巴国内镜像源或下载完整离线包手动安装串口监视器空白波特率不匹配/串口被占用/板子未复位确认波特率一致烧录后重新打开监视器手动复位板子串口输出乱码TX/RX接反/波特率不一致检查交叉接线确认波特率设置端口列表里没有开发板USB驱动未安装/数据线仅充电线安装CH340等驱动换数据线再试编译无法上传端口选择错误/开发板型号选错/串口被其他软件占用确认端口和板型关闭占用串口的软件Uno无法上传程序Bootloader损坏用另一块Arduino按ISP方式重新烧录引导程序电机一启动单片机就重启供电不足/电源共地没做好独立供电合理分配电源确保共地代码里用了String程序莫名卡死堆碎片化/内存耗尽改用char数组和snprintf这张表的每一行都是我在各种教程、论坛和实际调试中汇总出来的经验建议你先保存下来遇到问题先对表排查。5.2 进阶路线应用层、驱动层和嵌入式Linux怎么选当你把Arduino玩得比较熟了就会面临一个选择接下来往哪个方向深入如果你对“硬件底层怎么工作”感兴趣想搞明白芯片内部发生了什么那可以往裸机开发方向走。学习STM32、ESP-IDF框架接触寄存器操作、中断优先级、DMA传输、FreeRTOS实时操作系统。这条路不需要Linux知识但需要你对电子线路有一定理解是很多硬件工程师的成长路径。如果你更关注“大型嵌入式系统”那就得接触嵌入式Linux。嵌入式Linux驱动开发是另一个世界你得懂Linux内核模块怎么编写、设备树怎么配置、字符设备驱动框架是什么还得会交叉编译工具链。这时候Arduino那套IDE就不适合了你需要一台运行Linux的电脑或者虚拟机配合交叉编译环境来开发。还有一条路是“应用层界面开发”比如LinuxQt5嵌入式开发课程和相关岗位。这类职位重点在GUI界面、业务逻辑、通信协议写出来的代码跑在嵌入式设备上但主要是应用层逻辑。这也就是最开始那个问题“应用层开发是不是嵌入式”的答案来源——它确实是嵌入式系统的一部分但和驱动开发的思维模式差别很大。我的建议很明确不管未来选哪条路先用Arduino把“软硬结合的直觉”培养起来。你不需要在设计PCB之前先学会布局但你要知道一个传感器是怎么把物理量变成电信号、一个PWM信号是怎么控制电机转速的。这些基础感觉一旦建立后面学STM32或Linux驱动都会顺畅很多。5.3 关于烧录、版本和库管理再补充几个独家建议最后分享几个不容易在教程里看到的操作经验都是踏踏实实踩过坑才总结出来的。第一ESP32和ESP8266的版本管理一定要记牢。不同版本的核心库对API的行为可能有变化同一个代码在ESP32 2.x和3.x版本下的编译结果可能会有差异。我建议在一个项目里锁定一个固定的开发板版本不要频繁升级否则你可能花一天时间查一个“昨天还能编译”的代码为什么突然报错。要是换电脑或者重新搭环境最好用离线包恢复到之前的版本。第二Arduino的库文件夹要定期清理。Windows下库默认在文档\Arduino\libraries装得多了以后每次编译IDE都要扫描所有库启动和编译都会变慢。更麻烦的是某些库之间还有版本冲突。我习惯为每个项目单独建一个libraries文件夹在IDE里通过项目文件指定的方式管理依赖。第三代码里多写注释尤其是为什么这么写的注释。嵌入式项目的硬件和软件耦合度极高你调试时发现“这个引脚不能用作PWM输出”或者“这里必须延时50ms等传感器稳定”这些“为什么”如果不写下来三个月后再看自己的代码你一定会后悔。第四尽量给每个传感器模块单独测试后再组装进大项目。很多人喜欢一次把所有模块接好然后一次性调试。但这样一旦出问题排查范围会非常大。我的做法是先点亮LED确认主控工作再单独接超声波测距并打印数据再单独接电机测试PWM控制最后才把所有模块组装到一起联调。这个过程看起来多花了时间实际是总时间最短的做法。
返回列表