ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

基于51单片机的程控滤波器设计:原理、电路与调试

基于51单片机的程控滤波器设计:原理、电路与调试 简介以AT89S52单片机为核心的程控滤波器设计与实现论文资料面向电子、自动化、嵌入式方向的本科毕业设计及课程设计学习者。文档从滤波器基础概念、模拟与数字滤波器结构差异入手系统讲解AT89S52单片机的主要性能、引脚功能、存储器结构及定时器应用并结合DAC0832芯片介绍硬件接口与A/D转换实现方案。第3章以后重点论证系统总体方案涵盖放大电路与滤波电路选型、理论计算以及基于C语言的程序编写思路最终实现滤波器参数的动态调节与对不同频率信号的适应性控制。资源包为单个docx文档共1个文件大小1.84MB内容结构清晰包含摘要、目录、原理分析、方案论证与设计实现全过程适合需要完整参考论文框架、硬件选型思路和代码设计逻辑的读者阅读。目前已有67人学习下载可作为毕业设计写作和单片机信号处理实践的实用参考。1. 为什么“程控滤波器”值得用单片机做实验室里调信号最烦的就是手里一堆电阻电容为了找一个截止频率来回换元件。程控滤波器要解决的正是这个问题用单片机改变滤波器的等效电阻或时钟让低通、高通、带通的截止频率在几毫秒内切换不用动烙铁。这类装置在信号采集前端、音频带限、传感器调理和通信基带里都很常见课程设计和毕业设计更是常客。反直觉的一点是做出一个能用的程控滤波器并不需要昂贵的DDS或专用滤波芯片一颗几块钱的51单片机加数字电位器就能覆盖音频段到几十千赫兹的调节范围。本文按“方案选型→电路搭建→程序控制→参数标定→调试技巧”这条线展开读者跟着做就能复现一个可通过按键或串口设定截止频率的滤波器并知道偏差出在哪里。2. 单片机程控滤波器的方案选型与硬件电路搭建2.1 三种主流实现方案对比实现程控滤波器常见的有三种路线。第一种是用数字电位器替代有源滤波器里的固定电阻配合运放构成Sallen-Key或多反馈拓扑单片机通过SPI/I2C调整电位器阻值从而改变截止频率。第二种是使用开关电容滤波器芯片比如MF10、MAX260/262单片机通过改变时钟频率来改变中心频率或截止频率这种方式频率范围可以做得很宽但芯片成本高、外围电路稍复杂。第三种是用单片机输出PWM经积分得到模拟电压再去控制压控运放或变容二极管思路直观但线性度和温漂难控制。从课程设计和实际制作的性价比看数字电位器加运放是首选。它元件少、原理清晰、调试直观频率覆盖从几十赫兹到几十千赫兹足以应对绝大多数信号调理场景。下面是三种方案的综合对比方案调节机制频率范围精度成本调试难度数字电位器运放改变RC时间常数10Hz~100kHz依赖电位器精度低低开关电容滤波器改变时钟频率0.1Hz~100kHz高较高中PWMDAC压控改变控制电压受限于VCO特性一般中较高2.2 核心电路Sallen-Key低通滤波器以最常见的二阶Sallen-Key低通为例电路拓扑为同相比例放大器后端接两节RC网络。取R1R2R、C1C2C时截止频率表达式为fc 1 / (2πRC)当单片机把数字电位器调到某个阻值R对应一个截止频率。要覆盖较宽的频率范围一般把R做成可调而C固定通过切换电容来换频段。这个电路有一个容易被忽略的点就是Sallen-Key结构里两个电阻要求同步变化因此需要双通道数字电位器或者用两片单通道电位器由单片机同步写值。运放选型方面LM324价格便宜但在几十千赫兹后增益带宽积会拖累实际频率响应想做高一点的频率就换OP07或TL072前者的低漂移适合直流耦合后者输入阻抗高、转换速率快。对于音频范围LM324完全够用后续的分析和参数也以它为基础。2.3 数字电位器选型与电路连接数字电位器常见型号有X9C103、MCP4131、AD5206等。X9C103是3线加减式接口阻值分99档便宜但线性度一般。MCP4131是SPI接口、7位分辨率128档线性度好且价格低适合与51或STM32连接。以MCP4131-10k为例标称阻值10kΩ每档步进约78.7Ω。单片机和MCP4131的连接非常简单只需要四根线VDD接3.3V或5VVSS接地SCK接单片机时钟引脚SDI接单片机MOSI串行数据输入CS接单片机普通IO口低电平有效在Sallen-Key电路里把R1、R2替换为两片MCP4131的P0W-P0A端单片机分别锁存两个芯片的控制值。注意数字电位器的抽头端P0W与P0A之间才是可调电阻P0B端不使用。接线时不要把P0A和P0B方向接反否则阻值变化规律会反过来。2.3.1 电路搭建时容易忽略的三个细节第一数字电位器的寄生电容一般在几十皮法量级频率超过几十千赫兹时会产生相位滞后实际截止频率会比理论值偏低需要在下文参数标定阶段补偿。第二MCP4131的供电电压直接影响模拟开关的内阻电源纹波会耦合到信号通路建议在VDD引脚就近放一个100nF去耦电容。第三如果使用两片电位器同步调阻务必在程序里做到“先备好两个值再同时拉低两片CS”否则先写入的一片会让通道增益瞬间跳变输出会产生一个毛刺。实际测试中这个毛刺在音频段表现为“咔哒”声就是写入时序不一致造成的。3. 单片机控制程序51通过SPI驱动MCP41313.1 模拟SPI驱动代码MCP4131的SPI时序要求16个时钟周期先送命令字节再送数据字节。命令字节0x00表示写易失性抽头位置数据字节的低7位为抽头值。我一般直接用51单片机的普通IO口模拟SPI因为MCP4131速率不高模拟方式足够稳定还省去硬件SPI引脚的束缚。以下是在STC89C52上基于C51的驱动代码#include reg52.h #include intrins.h // 引脚定义按实际接线修改 sbit SCK P1^0; sbit SDI P1^1; sbit CS1 P1^2; // 电位器1 sbit CS2 P1^3; // 电位器2 // 模拟SPI发送16位数据 void spi_send_16bit(unsigned char cmd, unsigned char data_byte) { unsigned char i; CS1 0; // 拉低片选开始通信 for (i 0; i 8; i) // 先发命令字节 { SCK 0; if (cmd 0x80) // 高位先出 SDI 1; else SDI 0; _nop_(); SCK 1; // 上升沿锁存数据 cmd 1; } for (i 0; i 8; i) // 再发数据字节 { SCK 0; if (data_byte 0x80) SDI 1; else SDI 0; _nop_(); SCK 1; data_byte 1; } SCK 0; CS1 1; // 释放片选 }这段代码的核心是SCK上升沿写入一个二进制位先发命令字节0x00再发抽头值。MCP4131的抽头值是7位有效所以数据字节最大0x7F对应10kΩ满量程。实际操作中如果直接调用这个函数两个电位器会依次写入中间存在时间差。更稳妥的写法是准备好两个数据值然后统一拉低片选// 同时更新两个电位器 void set_cutoff_freq(unsigned char tap1, unsigned char tap2) { unsigned char i; CS1 0; CS2 0; // 两片同时选中 // 先发第1片的命令和数据 for (i 0; i 16; i) { SCK 0; if (i 8) { SDI (i 7) ? 0 : 0; // 命令字节0x00 } else { SDI (tap1 0x40) ? 1 : 0; tap1 1; } _nop_(); SCK 1; } // 再发第2片 for (i 0; i 16; i) { SCK 0; if (i 8) { SDI 0; } else { SDI (tap2 0x40) ? 1 : 0; tap2 1; } _nop_(); SCK 1; } SCK 0; CS1 1; CS2 1; }上面这段代码要注意一个细节就是两片共用一个SPI总线时片选必须同时有效数据在总线上依次排列。因为MCP4131在CS拉低期间会持续监听时钟所以发送完第一片的数据后不能把CS1拉高而是等第二片数据也发送完毕后再统一释放。这是很多人写双通道数字电位器驱动时容易忽略的时序问题。3.2 串口指令接口设计实物做出来之后最常用的操控方式就是串口发送指令设定频率。用51单片机的串口1接收字符解析成电位器档位。代码如下void UART_Init(void) { TMOD 0x20; // 定时器1工作在模式28位自动重装 TH1 0xFD; // 波特率9600晶振11.0592MHz TL1 0xFD; PCON 0x00; SCON 0x50; // 串口模式1允许接收 TR1 1; ES 1; EA 1; } void UART_Isr() interrupt 4 { unsigned char rx; if (RI) { RI 0; rx SBUF; if (rx 0 rx 9) { // 把数字字符解析为档位0~127 tap_value (rx - 0) * 12; if (tap_value 127) tap_value 127; set_cutoff_freq(tap_value, tap_value); } } }这段代码里有个取值技巧就是数字字符转档位时直接乘以12把0~9映射到0~108虽然没有用满MCP4131的全部128档但避开了接近满量程时线性度变差的区间。这个区间通常在最后10%的抽头位置实际阻值会偏离标称值需要看数据手册的“满量程端非线性”指标。3.3 与定时器配合实现自动扫频如果不想手动一个个输入可以让单片机自动从低到高扫频。实现方式是用定时器0产生一个周期中断每次中断把tap_value加1再调用set_cutoff_freq更新电位器。扫描间隔取50ms这样从0到127扫完大约6.4秒适合在调试时接上示波器观察系统幅频响应变化。定时器初值计算公式为初值 65536 - (振荡频率 / 12 / 期望中断频率)以11.0592MHz晶振、20Hz中断频率为例初值约为46165换算成十六进制就是0xB455。注意定时器中断服务函数里不要做串口发送等耗时操作只更新档位和标志位串口上报交给主循环处理避免中断嵌套打乱SPI时序。4. 截止频率参数计算与实测校准4.1 理论截止频率对照表前文给出公式fc 1/(2πRC)当C固定时不同R对应不同频率。以下以C10nF为例列出MCP4131-10k在不同档位下的理论截止频率抽头值实际阻值(kΩ)截止频率(Hz)00.0787202019161.33811894322.5976128483.8564126645.1153111806.3732497967.63120851128.890179012710.0781579如果C换成100nF所有频率除以10。从表里能看到一个问题抽头值低档位时频率变化非常快每档差几千赫兹高档位时每档只差几十赫兹。这是对数特性也是数字电位器方案的天然限制。想要在整个范围内有均衡的分辨率一般是把低通、高通做成多档电容切换再配合电位器细调。4.2 实测校准步骤理论值只能作为参考实际电路中的运放输入电容、数字电位器寄生电容、面包板走线电容都会让频率往下偏。校准的常用设备是一台信号发生器和一个万用表或示波器。以校准低通滤波器的截止频率为例标准做法是保持输入正弦波幅值不变从高到低改变信号频率观察输出幅值降到输入的0.707倍时对应的频率点。校准步骤如下设定单片机抽头值为某个固定值比如64。信号发生器输出正弦波频率从远高于理论截止频率处开始逐步降低。示波器读取输出幅值记录Vout/Vin0.707处的频率。如果实测频率高于目标值说明等效电阻偏小增大抽头值低于目标值则减小抽头值。重复二分法查找直到误差在5%以内。这个二分法校准的收敛速度很快。比如目标是3kHz抽头值64时实测是2.78kHz说明阻值偏大下一步把抽头值改成48再看实测值变化逐次逼近目标区间。比手动一个档位一个档位试效率高得多。4.3 温度与电源电压对精度的影响MCP4131的端到端电阻温度系数在数据手册上一般标为±300ppm/℃左右也就是说温度从25℃升到45℃10kΩ的满量程电阻可能变化60Ω对应截止频率漂移不到1%。这个量级对音频应用完全无感但如果信号链路里有直流分量需要精确定标就不能忽略。更大的误差源其实来自电源电压。数字电位器的内部模拟开关导通电阻会随VDD波动而改变当VDD从5V降到4.5V抽头导通电阻可能增加几十欧姆。解决方法是给单片机和电位器单独用一片低压差线性稳压器供电而不是直接从USB取电。USB供电在负载波动时纹波明显数字电位器的阻值会跟着抖输出波形上能直接看到幅度调制。5. 调试技巧用扫频法和按键验证整机指标5.1 快速判断电路是否正常的三步法接好电路后不要急着直接测截止频率参数先做三步快速检查。第一步用万用表量MCP4131的P0W到P0A之间的电阻确认每个抽头值对应的阻值单调且大致符合线性关系。如果某几个档位阻值跳变异常多半是SPI时序问题导致写入值错误重点检查SCK空闲电平和CS释放时机。第二步运放输出端接示波器用手触碰输入端看是否有明显的50Hz工频干扰波形被放大或滤除以此判断滤波器是否在工作。第三步输入一个1kHz正弦波用单片机把抽头值从0慢慢加到127观察输出幅值是否随着截止频率降低而减小。这三步过了整机基本就通了。5.2 按键调速与数码管显示的结合实际使用中不一定挂电脑串口可以用按键做本地控制数码管显示当前档位或频率。接线方法是用P2口的八个引脚接数码管段码P3口接两个按键一个加一个减。按键消抖用定时器扫描的方式主循环每10ms检测一次按键状态。数码管显示可以通过查表函数实现unsigned char code seg_table[] {0xC0, 0xF9, 0xA4, 0xB0, 0x99, 0x92, 0x82, 0xF8, 0x80, 0x90}; void display_number(unsigned char num) { P2 seg_table[num / 10]; P3 0x01; // 选中十位 delay_ms(2); P2 seg_table[num % 10]; P3 0x02; // 选中个位 delay_ms(2); }注意两位数码管扫描显示需要轮流点亮刷新频率必须高于50Hz否则人眼能看出闪烁。这里delay_ms(2)配合两次扫描整体周期约4ms刷新率250Hz没有闪烁问题。按键每按一次就把tap_value加1或减1再调用set_cutoff_freq刷新电位器。这种本地操作方式省去上位机在实验室环境里比串口命令更直观。5.3 从低通扩展到带通与带阻如果做完整章验证后发现还有余力可以把Sallen-Key低通和高通级联构成带通滤波器。实现方式并不复杂在原有低通电路后面再接一级高通两级间用电压跟随器隔离。单片机的两个数字电位器分别控制低通级和高通级的截止频率程序里用一个结构体保存两组抽头值通过按键切换调节对象。切换高通级时需要翻转数字电位器的接入方向也就是把P0W接输入、P0A接地。这样程序逻辑虽然不变但截止频率的计算公式中R还是同一个值只是滤波器拓扑不同。带通中心频率为低通截止频率和高通截止频率的几何平均值带宽则取决于两者的间距。调试时先从低通级调起用扫频法确认低通曲线正常再调高通级最后合并观察带通响应。实测中两级之间如果没有加缓冲负载效应会让两个频点互相拉偏这是带通扩展中最常见的坑加一颗运放做电压跟随就能解决。本文还有配套的精品资源点击获取
返回列表