TA的每日心情  | 无聊 2016-10-8 20:34 | 
|---|
 
  签到天数: 10 天 连续签到: 1 天 [LV.3]偶尔看看II 
举人 
 
 
	- 积分
 - 604
 
 
 
 
 | 
 
 
试了好多种采样率,最终发现以我的水平,1K的采样率,这个板子才能正常采集计算并输出,可是1K的采样率能处理什么信号呢,重低音大概是在150Hz以下,于是就做了个截止频率150Hz的滤波器; 
 
目的:学会用C语言实现FIR滤波器; 
 
既然采样率1K,1ms的时间够MCU做21次乘加运算了,就来个20阶的,程序如下:- [hide]/* Private functions ---------------------------------------------------------*/
 
  
- /**
 
 -   * @brief  systick_init
 
 -   * @param  None
 
 -   * @retval None
 
 -   */
 
 - #define nus 1000  // 1000us采样一次,1K的采样率
 
 - static uint16_t fac_us;
 
 - void systick_init(void) 
 
 - {
 
  
-         SysTick_CKSource_Enable(SYSTICK_CKSOURCE_HCLK_DIV8);        // 选择HCLK/8
 
 -         fac_us=SystemCoreClock/8000000;            // 为系统时钟的1/8   
 
 - }
 
  
- /**
 
 -   * @brief  fir_lp
 
 -   * @param  None
 
 -   * @retval None
 
 -   */
 
 - const uint16_t gain[21] = {
 
 -         0,     96,    208,    124,      0,      0,      0,    869,   4518,
 
 -      8236,   9816,   8236,   4518,    869,      0,      0,      0,    124,
 
 -       208,     96,      0
 
 - };
 
 - static uint16_t buffer[21];
 
 - void fir_lp(void)
 
 - {                
 
 -         uint32_t output = 0;
 
 -     uint32_t temp = 0;
 
 -     static uint8_t j = 0;
 
 -     uint8_t i;
 
 -         SysTick->LOAD=nus*fac_us;   // 时间加载                           
 
 -         SysTick->VAL=0x00;          // 清空计数器
 
 -         SysTick->CTRL|=SysTick_CTRL_ENABLE_Msk ;        // 开始倒数
 
 -     
 
 -     if((j++) < 128)
 
 -             led_on(4);
 
 -         else
 
 -             led_off(4);
 
 -         
 
 -     for(i = 0;i < 21;i++)
 
 -         buffer[i-1] = buffer[i];    // 数据移位   
 
 -     buffer[20] = ADC1->RDTR;    // 读出上一次转换结果
 
 -     for(i = 0;i < 20;i++)
 
 -         output += gain[i]*buffer[i];   // 计算结果
 
 -     
 
 -     ADC_SoftwareStartInsertedConv_Enable(ENABLE);
 
 -     DAC_SetDAC1Data(DAC_ALIGN_12B_R,(uint16_t)(output >> 15));    // 将结果送入DAC,截位截到接近满输出
 
 -     DAC_SoftwareTrigger_Enable(DAC1,ENABLE);
 
 - //  while(ADC_GetBitState(ADC_FLAG_EOC) == RESET);  // 等待转换结束
 
 -  
 
 -     printf("\n\r%4d--%8x\r\n",buffer[20],(uint16_t)(output >> 15));
 
 -         do
 
 -         {
 
 -                 temp=SysTick->CTRL;
 
 -         }
 
 -         while(temp&0x01&&!(temp&(1<<16)));              // 等待时间到达   
 
 -         SysTick->CTRL&=~SysTick_CTRL_ENABLE_Msk;        // 关闭计数器
 
 -         SysTick->VAL =0X00;       // 清空计数器         
 
 - }
 
  
 
- /**
 
 -   * @brief  Main program.
 
 -   * @param  None
 
 -   * @retval None
 
 -   */
 
 - int main(void)
 
 - {
 
 -     /* 初始化 */
 
 -     systick_init();
 
 -     led_456_init();
 
 -     usart_init();
 
 -     adc_init();
 
 -     dac_init();
 
 -         
 
 -     while (1)
 
 -     {
 
  
-         fir_lp();
 
 -         
 
 -     }
 
 - }[/hide]
 
  复制代码 这个滤波器的结果还过得去,也算一个信号处理系统了,交作业的时间就到期了,好捉急啊,没时间再做其他东西了。 
以下图片为不同频率时输入输出对比效果,黄色为输入,白色为输出; 
 
 
 |   
 
  
  
  
 
 
 |