在线情况
楼主
  • 头像
  • 级别
    • 积分8
    • 经验100
    • 文章7
    • 注册2011-12-21
    探讨如何计算msp430采集到的正弦信号的频率
    [P][SIZE=2]最近对如何计算正弦信号的频率感觉非常纠结,我试了不同的方法,依然得不到像样的结果。[/SIZE][/P][P][SIZE=2]使用msp430F449采集250个数据,采样周期遵守奈奎斯特定律。采集到的数据用于计算信号频率。[/SIZE][/P][P][SIZE=2]为了保证数据光滑,我使用相邻三点相加取平均的方法进行平滑处理。[/SIZE][/P][P][SIZE=2]我主要使用了两种方法用于计算频率:[/SIZE][/P][P][SIZE=2]1. 正弦信号有最高值和最低值,最低值两边的值都比其大,最高值两边的值都比其小,我使用逐步比较的方法计算最低值和最高值,如果前一值比其大,后一值也比其大,其值为最低值,其对应的位置亦知道;对最高值也一样,如果前一值比其小,后一值也比其小,其为最大值,然后再找到第二个最低值所在的位置。第一个最低值,最高值,第二个最低值相应的位置获得后,就可以根据采样周期计算频率。[/SIZE][/P][P][SIZE=2]2.使用逐步比较的方法,首先找到最高值和最低值的大小,然后从头将数据跟最低值和最高低比较,分别找到其位置,来获得其所在的位置,进而计算频率。[/SIZE][/P][P][SIZE=2][/SIZE][/P][P][SIZE=2]最后得到的频率变化比较大,一点也不稳定。计算得到的最大电压值跟实际值一致,过程应该是没错的。[/SIZE][/P][P][SIZE=2]有人告诉我,使用微分的方法也可能可以,但是精确度低。[/SIZE][/P][P][SIZE=2]大家有没有好的办法进行处理。请不怜赐教。非常感谢![/SIZE][/P]
    [ 此贴最后由DC在2011-12-21 17:32:07编辑过 ]
    微控网感谢您的参与
    在线情况
    2
    • 头像
    • 级别
    • 门派
    • 职务总版主
    • 声望+9
    • 财富5
    • 积分3065
    • 经验390701
    • 文章6744
    • 注册2006-03-07
    [P]你好:
    楼主的贴子描述非常详细,让人看了一目了然。很舒服...得赞一下。
    类似这样使用MCU的方式来测算波形的频率,我在一些资料上也有看到过类似楼主提及的方法。就是利用取样波形的值进行ADC采样。从中找到上升或下降的方向,然后查找最低点到最低点或最高点到最高点的周期时间测量。这种方式有一定成效,但也有可能有些决点。就是效率低还有其他问题。比如频率高了,带宽的问题。[/P][P]而我有点疑问是,不知楼主所测的信号的信号频宽是在什么范围呢?[/P][P]信号是否是有一个有规律性的波形?
    纯属就是只测频率的,而其他不用管?
    还是对AC工频电压测量?
    如果只是一个稳定的信号,我觉得你可以采取一个办法。就是使用整形法!取样小信号波形,然后通地一个施密特电路将其整容为方波。然后利用MCU的边沿中断或捕获形式来测出方法的时长。这样便比简便实现测量出信号的频率了...。我不知道这个方法对楼主是否适用,所以我作出了上述的提问。
    谢谢![/P]
    [COLOR=#0000ff]欢迎发贴分享设计心得、开源DIY...[/COLOR]
    在线情况
    3
    • 头像
    • 级别
      • 积分8
      • 经验100
      • 文章7
      • 注册2011-12-21
      [P]我在这里提到采集正弦波,是因为正弦波容易被大家理解,我所采集的真实波形是近似正向正弦波。版主提到的整形法我也考虑过,但是整形法存在的一个问题是:将波形整容为方波需要在一定的阈值下进行,这样精确度不高。 比如,当波形电压值达到0.3伏时,才能变形为方波,0.3伏之前的低值波就无法使用,这样计算得到的频率准确度就差了些。[/P][P]我所采集的信号频宽比较小,大约在0.6s,也就是在1分钟内大约100个波形。我设定的采集频率大约为250Hz,采集250个点,最终得到的波形频率不稳定,我不禁怀疑采集频率是不是太低。另外我还需要测量占空比,其它的就不在乎了。[/P][P]不管怎样,版主您提到的整形法我觉得我还是要试一下,不试怎么会知道不行呢?[/P][P]非常感谢版主![/P][P][P]因为我采集的数据比较少,如果采用定点FFT进行计算如何?[/P][P]我从来没有使用过FFT计算,请问我这样的数据进行FFT计算是否具有可行性?[/P][/P][P] [/P]
      [ 此贴最后由DC在2011-12-22 12:22:25编辑过 ]
      微控网感谢您的参与
      在线情况
      4
      • 头像
      • 级别
        • 积分8
        • 经验100
        • 文章7
        • 注册2011-12-21
        [P][CODE]
        //---------------------function name: calc_cycle
        void calc_cycle(unsigned int *volt_value)
        {
          unsigned int i=0;
          unsigned long hex_value;
          unsigned int temp_low = 0;
          unsigned int temp_high = 0;
          unsigned int temp_seclow = 0;
          unsigned int number_low = 0;
          unsigned int number_high = 0;
         
          //--------------将16进制数转为10进制数
          //10进制数为乘100的数,绕开小数计算
          for (i=0;i<Num_of_Results;i++)
          {
             hex_value = volt_value;
           hex_value = (hex_value <<5) + volt_value;           // caltmp=Hex_val *33
           hex_value = (hex_value << 3) + (hex_value << 1);       //caltmp=caltmp*10
             hex_value >>=12;
             volt_value = hex_value;
          }
         
          //---------------寻找第一个最小值
          for (i=0;i<Num_of_Results-1;i++)
          {  if (volt_value[i+1]<volt_value && volt_value[i+1]==volt_value[i+2])
              {
              temp_low=i;
              break;
              }
             else continue;  
          }  
         
         
          //-----找到第一个最小值后,寻找第一个最大值
          for (i=temp_low+1;i<Num_of_Results-1;i++)//locat the first max value
          {   if (volt_value[i+1] >volt_value && volt_value[i+1]==volt_value[i+2])
              {
                 temp_high = i+1;
                 break;
              }
              else continue;
          }
         
          //---------找到第一个最大值后,寻找第二个最小值    
          for (i=temp_high+1;i<Num_of_Results-1;i++) // locate the second minimum value
          { if (volt_value[i+1]<volt_value && volt_value[i+1]==volt_value[i+2])
              {
              temp_seclow=i+1;
              break;
              }
             
             else continue;
          }
         
          //----------计算两个半周期的样点数
          number_high = temp_high-temp_low;   ////上半周期采样点数
          number_low = temp_seclow-temp_high;  ///下半周期采样点数
         
          rate_dc(number_low,number_high,sum);    //频率计算子函数        
        }
        void rate_dc(int num_low,int num_high)
        {
          unsigned int rate=0 ;
          unsigned int r[3];
          rate = 13944/(num_low+num_high); // the SHT0_11 is about 0.004s, the rate in one minute is
                                 // 60/((num_low +num_high)*0.004)
        }

        [/CODE]
        以上是我计算处理数据,计算频率的关键函数。[/P][P]计算频率方法使用的是逐步比较法,寻找最先的最低值和最高值。[/P][P]最后计算得到的频率是每分钟内的周期数。[/P][P]我设定的采样周期为0.004s,信号发生器产生的方形波信号周期为0.6s,共采样250个点。[/P][P]我依然得不到正确的频率,求助,哪里有问题?crazy!!![/P]
        [ 此贴最后由DC在2011-12-22 12:24:01编辑过 ]
        微控网感谢您的参与
        在线情况
        5
        • 头像
        • 级别
        • 门派
        • 职务总版主
        • 声望+9
        • 财富5
        • 积分3065
        • 经验390701
        • 文章6744
        • 注册2006-03-07
        [P][QUOTE][B]下面引用由[U]xiaocheng_2007[/U]发表的内容:[/B]
        。我设定的采集频率大约为250Hz,采集250个点,最终得到的波形频率不稳定,
        [/QUOTE]
        你好:
        如果采集频率大约为250Hz的话,估计你被采样的的目标频率也只有几十HZ吧。对于这如此的低的信号,我想起一个办法。建议你使用微控推出的MCE9209电量计量芯片。可以利用这个芯片的工频频率计量出输入信号的频率。这个器件的ADC是16位的ADC对小信号非常敏感,通过他读取出来的信号频率是非常准确的。正好你的条件是近正弦信号、且幅度小、频带小的特点。另外,对于MCE9209的带宽为250HZ左右,对于你的几十HZ来说是足够了。这样只需你通过SPI读取频率寄存器出来的值/8/8948=便等于得出频率值了。
        这样的做法是需要增加一个外置芯片,成本大概5、6元左右。这样便可以减轻你的MCU处理不准确问题。非常方便。 [/P][P]链接:http://www.microcontrol.cn/LookDoc.asp?LookFileID=doc/MC/MCE9209/MCE9209#Menu=ChildMenu2
        你考虑一下吧,另外,如果要动用到FFT这种算法,我怕你的MCU吃不消。这FFT高档玩意我也没玩过;据用过F5的用户使用情况还是有所压力的,是否适用还不太清楚。
        我的意见是这样了,呵呵...欢迎其他网友提出些意见来...交流。[/P]
        [COLOR=#0000ff]欢迎发贴分享设计心得、开源DIY...[/COLOR]
        在线情况
        6
        • 头像
        • 级别
          • 积分8
          • 经验100
          • 文章7
          • 注册2011-12-21
          [QUOTE][B]下面引用由[U]DC[/U]发表的内容:[/B]

           
          你好:
          如果采集频率大约为250Hz的话,估计你被采样的的目标频率也只有几十HZ吧。对于这如此的低的信号,我想起一个办法。建议你使用微控推出的MCE9209电量计量芯片。可以利用这个芯片的工...[/QUOTE]
          非常感谢版主的建议,可是我不在国内。不管怎样,非常感谢版主的热心
          微控网感谢您的参与
          在线情况
          7
          • 头像
          • 级别
          • 门派
          • 职务总版主
          • 声望+9
          • 财富5
          • 积分3065
          • 经验390701
          • 文章6744
          • 注册2006-03-07
          [P]呵呵,不客气[EM12],有空欢迎常来微控论坛帮助其他网友解答问题....。[/P][P]哥们,在国外那个研究所工作啊?真利害~[EM10][/P]
          [ 此贴最后由DC在2011-12-26 19:09:47编辑过 ]
          [COLOR=#0000ff]欢迎发贴分享设计心得、开源DIY...[/COLOR]
          在线情况
          8
          • 头像
          • 级别
            • 积分21
            • 经验516
            • 文章33
            • 注册2009-10-13
            [P]通过硬件电路转换成方波,然后再测比较好啊。[/P]
            再思考一下
            在线情况
            9
            • 头像
            • 级别
            • 门派
            • 职务总版主
            • 声望+9
            • 财富5
            • 积分3065
            • 经验390701
            • 文章6744
            • 注册2006-03-07
            我本来也是想叫他是这样处理的,但他的信号的动态幅度问题,并没有这样做。
            [COLOR=#0000ff]欢迎发贴分享设计心得、开源DIY...[/COLOR]
            在线情况
            10
            • 头像
            • 级别
              • 积分2
              • 经验80
              • 文章2
              • 注册2011-12-30
              [EM06]围观,学习了
              微控网感谢您的参与
              在线情况
              11
              • 头像
              • 级别
                • 积分8
                • 经验1040
                • 文章16
                • 注册2011-10-31
                授教了。。。
                微控网感谢您的参与
                在线情况
                12
                • 头像
                • 级别
                  • 积分1
                  • 经验75
                  • 文章1
                  • 注册2012-03-01
                  学习了............
                  微控网感谢您的参与
                  Powered by LeadBBS 9.2 .
                  Page created in 0.2808 seconds with 8 queries.