精华内容
下载资源
问答
  • 信号进入电路后,先用最大值电路和峰值比较器区分出正弦波和三角波,再用过零比较器和异或门区分出矩形波,然后得到代表波形的识别信号,最后用STC12单片机进行波形识别。实验结果表明该系统可以在50Hz-9kHz范围内对...
  • 2021年全国电子设计竞赛J题
  • 频谱分析(50Hz~200Hz,其他范围内应该也可以)包括了基频,3,5,7次谐波的峰值,波形识别可识别正弦,方波,锯齿波,三角波。硬件为正点原子精英版3.5‘TFTLCD,直接烧写肯定能用。(我的博客里有程序说明)
  • 基于STC12单片机的波形识别系统设计.pdf
  • 波形识别

    千次阅读 2021-01-26 17:26:57
    波形识别: waveEncode: 字符转换成波形; waveDecode:将波形转换成字符; 无线通信实现传输信息 完整源码:https://download.csdn.net/download/zhangxiaobo0715/14934577 waveEncode.c #include <sys/...

    波形识别: 
    waveEncode: 字符转换成波形;
    waveDecode:将波形转换成字符;

    无线通信实现传输信息

    完整源码: https://download.csdn.net/download/zhangxiaobo0715/14934577

    waveEncode.c

    #include <sys/types.h>
    #include <sys/stat.h>
    #include <string.h>
    #include <stdlib.h>
    #include <unistd.h>
    #include <stdio.h>
    #include <time.h>
    
    #include <math.h>
    #include "waveRecog.h"
    
     static signed char crc_8_ccitt(signed char* msg, int len) 
     {
        int crc =  0xFF;  
        int polynomial = 0x07;  
        signed char bit, c7;
        int b = 0, i = 0;
        
        for (b = 0; b < len; b++) 
        {
            for (i = 0; i < 8; i++) 
            {
                bit = ((msg[b] >> (7 - i) & 1) == 1)?1:0;
                c7 = ((crc >> 7 & 1) == 1)?1:0;
                crc <<= 1;
                if (c7 ^ bit)
                    crc ^= polynomial;
            }
        }
        crc &= CRC_BIT;
        return (signed char)crc;
    }
    
    // 浮点的正弦波转成整数
    void float2Byte(double* sequence, int length, signed char* result)
    {
        int i = 0;
        for(i=0; i < length; i++)
        {
            result[i] = (signed char)((sequence[i] * FLOAT_TO_BYTE_BASE));
        }
    }
    
    // 两端磨平,降低两端的权值,凸出中间部分权重,提高准确率
    void smoothBurst(double* input, int length)
    {
        int peaks = (int)(length /40);
        int i = 0;
        for (i=0; i<length; i++)
        {
            if (i < peaks)
            {
                input[i] = input[i]  * i /peaks ;
            } 
            else if ( i > length - peaks)
            {
                input[i] = input[i] * (length - i - 1)/peaks;
            }
        }
    }
    
    // 头部用于调相的正弦波
    void phaseSequence(signed char* output)
    {
        double signal[SAMPLES_PER_BURST]; 
        double innerMultiplier =  (HEAD_SCH_FREQUENCY* 2 * M_PI)/ SAMPLING_RATE ;
        int i = 0;
        for(i = 0; i < SAMPLES_PER_BURST; i++){
          signal[i] =  cos(innerMultiplier * i); 
        }
    
        smoothBurst(signal, SAMPLES_PER_BURST);
        float2Byte(signal, SAMPLES_PER_BURST, output);
    }
    
    // 信号调制
    void encodeBurst(char input, signed char* output)
    {
        double signal[SAMPLES_PER_BURST];
        int k = 0;
        int l = 0;
        double innerMultiplier = 0.0;
        memset(signal, 0, sizeof(double)*SAMPLES_PER_BURST);
        
        // 8种频率的信号调制到一起, CA(载波聚合)?
        for(k = 0; k < BITS_PER_BYTE; k++)
        {
            if( ((input >> k) & 0x1) == 0 )
            { 
                continue;
            }
            innerMultiplier = (2 * M_PI) / g_iFrequencies[k];
            for(l = 0; l < SAMPLES_PER_BURST; l++){
                signal[l] = signal[l] + ((cos(innerMultiplier * l)/BITS_PER_BYTE)); 
            }
        }
        smoothBurst(signal, SAMPLES_PER_BURST);   
        float2Byte(signal,SAMPLES_PER_BURST, output);
        return ;
    }
    
    void encodeStream(char* input, int lengthOfInput, signed char* outputresult, int* lengthOfOutput)
    {
        int i=0;
        int j=0;
        int ioutPos = 0;
        signed char crc;
        signed char *output = outputresult;
        #ifdef SUPPORT_NOISE
        //用当前时间点初始化随机种子,防止每次运行的结果都相同,  可以用于产生噪声
        time_t tm;
        time(&tm);
        unsigned int nSeed =(unsigned int)tm;
        srand(nSeed);
        #endif
    
        memset(&output[ioutPos], 0, SAMPLES_PER_BURST);  //初始化一段全0脉冲
        ioutPos += SAMPLES_PER_BURST;
        
        phaseSequence(&output[ioutPos]);  //产生一个固定频率的正弦波, 用于解码调相的脉冲序列
        ioutPos += SAMPLES_PER_BURST;
    
        encodeBurst(HEAD_0, &output[ioutPos]);  //头部脉冲
        ioutPos += SAMPLES_PER_BURST;
        
        encodeBurst(HEAD_1, &output[ioutPos]);  // 头部脉冲
        ioutPos += SAMPLES_PER_BURST;
        
        for(i=0;i<lengthOfInput;i++)
        {
            encodeBurst(input[i], &output[ioutPos]);  // 内容脉冲
            ioutPos += SAMPLES_PER_BURST;
        }
        
        crc = crc_8_ccitt((signed char*)input, lengthOfInput);
        encodeBurst(crc, &output[ioutPos]);  // crc校验脉冲
        ioutPos += SAMPLES_PER_BURST;
        
        encodeBurst(0, &output[ioutPos]);   // 尾部冗余量
        ioutPos += SAMPLES_PER_BURST; 
    
        *lengthOfOutput = ioutPos;
        return ;
    }
    
    int main()
    {
        FILE *fp        = NULL;
        char fileName[64] = "inputWave.pcm";
        char input[] = "abcdefghijklmnopqrstuvwxyz 0123456789 ~!@#$%^&*()_+{}:";
        int lengthOfInput = strlen(input);
        int lengthOfOutput = 0;
        int iWriteLen = 0;
    
        char *output = (char *)malloc(SAMPLES_PER_BURST*(8+sizeof(input)));
        if(NULL == output)
        {
            TRACE_ERROR("No Mem!");
            return -1;
        }
        memset(output, 0 ,SAMPLES_PER_BURST*(8+sizeof(input)));
        
        fp = fopen(fileName,"wb");
        if(NULL == fp)
        {
            TRACE_ERROR("Create %s Failed!", fileName);
            free(output);
            return -2;
        }
        
        encodeStream(input,lengthOfInput,output,&lengthOfOutput);
        if(lengthOfOutput > 0)
        {
            iWriteLen = fwrite(output,1,lengthOfOutput,fp);
            if(iWriteLen != lengthOfOutput)
            {
                TRACE_WARN("File write error input length is %d, write length is %d",lengthOfOutput , iWriteLen);
            }
        }
        else
        {
            TRACE_ERROR("Encode error!");
        }
        fclose(fp);
        free(output);
        TRACE_INFO("Encode %s ok...",input);
        return 0;
    }
    
    
    
    

    waveDecode.c

    #include <sys/types.h>
    #include <sys/stat.h>
    #include <string.h>
    #include <stdlib.h>
    #include <unistd.h>
    #include <stdio.h>
    #include <math.h>
    #include "waveRecog.h"
    
    #define RECOG_THRESHOLD   (0.53) //0.4
    
    static signed char crc_8_ccitt(signed char* msg, int len) 
    {
        int crc =  0xFF;  
        int polynomial = 0x07;  
        signed char bit, c7;
        int b = 0, i = 0;
        
        for (b = 0; b < len; b++) 
        {
            for (i = 0; i < 8; i++) 
            {
                bit = ((msg[b] >> (7 - i) & 1) == 1)?1:0;
                c7 = ((crc >> 7 & 1) == 1)?1:0;
                crc <<= 1;
                if (c7 ^ bit)
                    crc ^= polynomial;
            }
        }
        crc &= CRC_BIT;
        return (signed char)crc;
    }
    
    double complexCalculate(signed char *signal, int lengthofsignal, double u)
    {
        int i = 0;
        double realSum = 0;
        double imaginarySum = 0;
        double realUnit = 0;
        double imaginaryUnit = 0;
        // 滤波    积分
        for(i = 0; i < lengthofsignal; i ++)
        {
            realUnit = cos(i * u) * signal[i] ;
            imaginaryUnit = sin(i * u) * signal[i];  // 防止相位相差180
            realSum = realSum + realUnit;
            
            imaginarySum = imaginarySum + imaginaryUnit;
        }
        // 均衡
        double realAve = realSum/lengthofsignal;
        double imaginaryAve = imaginarySum/lengthofsignal; 
    
        return sqrt( (realAve * realAve) + (imaginaryAve * imaginaryAve) );
    }
    
    
    double complexDetect(signed char *signal, int lengthofsignal, int index)
    {
        // 特征频点
        double innerMultiplier = (2 * M_PI) / g_iFrequencies[index];
        // 滤波积分
        return complexCalculate(signal, lengthofsignal, innerMultiplier);
    }
    
    double complexHead(signed char *signal, int lengthofsignal)
    {
        // 头部频点
        double u = 2 * M_PI * HEAD_SCH_FREQUENCY / SAMPLING_RATE;
    
        //滤波积分
        return complexCalculate(signal, lengthofsignal, u);
    }
    
    int streamdecode(double *StartSignals, int lengthofStartSignals, signed char *pcm_buf8,  int lengthofpcmbuf8, signed char *decoded, int lengthofDecoded)
    {     
        int i = 0;
        int j = 0;
        int k = 0;
        int kk = 0;
        int durations = lengthofpcmbuf8/SAMPLES_PER_BURST;
        double signal[BITS_PER_BYTE * BYTES_PER_BURST][durations];
        // 该Burst所有信道的原始信号能量
        for(i=0; i < durations; i++)
        {
            for( j = 0; j < BITS_PER_BYTE * BYTES_PER_BURST; j++)
            {
                signal[j][i] = complexDetect(pcm_buf8 + SAMPLES_PER_BURST*i, SAMPLES_PER_BURST, j);
            }
        }
     
        //归一化信号 
        for( i = 0; i < (BITS_PER_BYTE * BYTES_PER_BURST); i++)
        {
            for( j = 0; j < durations; j++)
            {
                signal[i][j] = signal[i][j] / StartSignals[i];
            }
        }
    
        int ivalue = 0;
        for( i = 0; i < durations; i++)
        {
            for( k = 0; k < BYTES_PER_BURST; k++)
            {
                signed char value = 0;
                for(j = 0; j < BITS_PER_BYTE; j++)
                {
                    // 归一化后的能量大于RECOG_THRESHOLD(0.53 理论上是0.5) 就检测到该信道为1,否则为0
                    if(signal[(k * BITS_PER_BYTE) + j][i] > RECOG_THRESHOLD)
                    { 
                        value = (signed char)(value | ( 1 << j));
                    }
    
                    // 信道噪声比较大, 信道能量在 RECOG_THRESHOLD 左右
                    /* TODO 信道差的处理
                            两种猜测,0和1,   后面做CRC的时候分别传入校验即可,但是质量差的点太多也无法恢复,如传输CRC的的信号质量差怎么办
                    */      
                    if((signal[(k * BITS_PER_BYTE) + j][i] > (RECOG_THRESHOLD - 0.1) && (signal[(k * BITS_PER_BYTE) + j][i] < (RECOG_THRESHOLD + 0.1))))
                    {
                      TRACE_WARN("Bad quality: %d:%f     %d \n",j,signal[(k * BITS_PER_BYTE) + j][i],ivalue);
                    }
                }
    
                // 得出信号值
                *(decoded+kk)=value;
                kk++;
                // 函数调用问题
                if(kk > lengthofDecoded)
                {
                    TRACE_ERROR("Decoded size is not enough\n");
                    return -1;
                }
            }
        }
    
        return 0;
    }
    
    static int findHead(char* signal, int lengthofsignal, int granularity)
    {
        int maxCorrelationIndex = -1;
        double maxCorrelation = -1;  // 如果噪声大,这个点可以调节,需要更多的噪声环境测量出一个合适的阈值
        double acceptedSignal = 0.01;
        int i=0;
     
        for(i = 0; i <= lengthofsignal - SAMPLES_PER_BURST; i += granularity)
        { 
            double corr = complexHead(signal+i,SAMPLES_PER_BURST);
            if (corr > maxCorrelation)
            {
                // 如果频率匹配且相位正确,那从这一点开始的积分的结果最大
                maxCorrelation = corr;
                maxCorrelationIndex = i;
            }
        }
        
        // 最大能量都小于可接受的能量  
        if (maxCorrelation < acceptedSignal && maxCorrelation > -1){
            maxCorrelationIndex = -1;
        }
        return maxCorrelationIndex;
    }
    
    int main()
    {
        int headIndex = 0;
        int i = 0;
        int iNeedLen = 0, ireadLen = 0,iPos = 0;
        int iGotHead = 0;
        int iBufSize =  SAMPLES_PER_BURST * HEAD_LEN;
        int ioutIndex = 0;
        int iFilePos = 0;
        unsigned char outStream[128];
    
        double startSignals[BITS_PER_BYTE] = {0,0,0,0,0,0,0,0};
        signed char *pcm_buf8 = NULL;
        FILE *fp = NULL;
        char fileName[] = "inputWave.pcm";
        fp = fopen(fileName,"rb");
        if (NULL == fp)
        {
            TRACE_ERROR("Open %s failed!",fileName);
            return -1;
        }
        pcm_buf8 = (signed char *)malloc(iBufSize);
        if(NULL == pcm_buf8)
        {
            TRACE_ERROR("No Mem!");
            fclose(fp);
            return -2;
        }
    
        while(1)
        {
            iNeedLen =  iBufSize - iPos;
            if (iNeedLen)
            {
                ireadLen = fread(&pcm_buf8[iPos],1,iNeedLen,fp);
                if((ireadLen != iNeedLen) && (0 == (iPos + ireadLen)))
                {
                    TRACE_WARN("Read file, Can't get enough data, expert:%d read :%d \n",iNeedLen,ireadLen);
                    break ;
                }
                iFilePos += ireadLen;
                iPos += ireadLen;
            }
            
            if(0 == iGotHead)
            {
                // 以20个样点为单位步进找到头部,步进越小查找的相位越精确
                headIndex = findHead(pcm_buf8,iPos,20);
                if(0 == headIndex)  //检测到头
                {
                    TRACE_INFO("Find head ");
                    // 头部信息的两个字节为0xAA(10101010) 0x55(01010101)
                    // 得到到所有物理信道,便于后面做归一化
                    for( i= 1; i < BITS_PER_BYTE ; i+=2)
                    {
                        startSignals[i] = complexDetect(pcm_buf8 + SAMPLES_PER_BURST, SAMPLES_PER_BURST, i);
                    }
                    for( i= 0; i < BITS_PER_BYTE; i+=2)
                    {
                        startSignals[i] = complexDetect(pcm_buf8 +(SAMPLES_PER_BURST*2), SAMPLES_PER_BURST, i);
                    }
                    // TODO   这里其实也可以把 头部两个字节(0xAA 和0x55)解析出来   ,头部解析出来就不需要 memmove
    
                    iGotHead = 1;
                }
                else if(0 < headIndex) //可能检测到头的位置,在某个位置有个能量极值点
                {
                    TRACE_INFO("May Be Get Head ");
                    
                }
                else //未检测到任何信息
                {
                    TRACE_INFO("No any Data , Have Read:%d headIndex:%d",iFilePos,headIndex);
                }
                iPos -= SAMPLES_PER_BURST;
                if (iPos > 0)
                    memmove(pcm_buf8, pcm_buf8 + SAMPLES_PER_BURST, iPos);
                continue;
            }
    
            streamdecode(startSignals,BITS_PER_BYTE,pcm_buf8,SAMPLES_PER_BURST,&(outStream[ioutIndex]),1);
            iPos -= SAMPLES_PER_BURST;
            // 这里可以把buf里面的内容都解析出来就不用 memmove
            if (iPos > 0)
                memmove(pcm_buf8, pcm_buf8 + SAMPLES_PER_BURST, iPos);
            
            TRACE_INFO("%d.Get 0x%x[%c] ",ioutIndex,outStream[ioutIndex],outStream[ioutIndex]);
            if(outStream[ioutIndex])
            {
                ioutIndex += 1;
                continue;
            }
            
            if(ioutIndex <= 1+HEAD_INFO_LEN)
            {
                TRACE_ERROR("Can't Get any info! File Pos:%d",iFilePos);
            }
            
    //        TRACE_INFO("%x  CRC:%x \n\n", outStream[ioutIndex - 1],(unsigned char)crc_8_ccitt(&outStream[HEAD_INFO_LEN], ioutIndex-1-HEAD_INFO_LEN));
            if (outStream[ioutIndex - 1] == (unsigned char)crc_8_ccitt(&outStream[HEAD_INFO_LEN], ioutIndex-1-HEAD_INFO_LEN))
            {
                outStream[ioutIndex-1] = 0; 
                TRACE_INFO("outstring is %s  ", &outStream[HEAD_INFO_LEN]);
            }
            else
            {
                TRACE_WARN("CRC error outstring is %s  ", &outStream[HEAD_INFO_LEN]);
            }
            break;
        }
            
        fclose(fp);
        free(pcm_buf8);
        return (0);
    }
    
    
    

    TODO: 

    1. 增加载波数量 - 即增加物理通道数量

    2. 提高载波频率 - 即提高负载

    3. 跳频 - 提高抗干扰能力

    4. 增加高能基波 - 相当于加入干扰因子

     

    展开全文
  • 硬件设备:TFTLCD显示屏+stm32f103zet6。引脚PA4通过DAC产生正弦波信号,可以调频率和幅度;引脚PC1通过ADC采集信号,代码里面有很多的FFT波形分析方法,但我目前只会分析出峰峰值,但其他代码可以给大佬参考。
  • 实现语音识别波形,通过录一段语音,用matlab识别波形并对语音信号进行处理
  • FFT与波形识别.zip

    2021-05-05 15:52:37
    两个文件夹,第一个是基础版本,第二个可以触屏改变采样频率,进而优化频率分辨率,使频谱分析更精确。
  • 雷达干扰matlab代码LPI-雷达-波形识别 在过去十年中广泛出现的汽车雷达面临着各种干扰攻击。 利用低截获概率 (LPI) 雷达波形作为基本解决方案之一,需要在截获接收器上使用准确的波形识别器。 已经研究了许多用于 ...
  • 为了使系统在理想的频率下具有高功率传输能力和效率,提出了一种基于波形识别的方法。 首先,建立了SP型WPT系统的空间状态模型,并基于频闪映射理论获得了理想和非理想工作频率下的波形。 其次,根据这些波形的特性...
  • waveRecog 波形识别

    2021-01-26 17:09:47
    波形识别
  • 波形识别.rar

    2021-10-25 10:31:17
    波形识别
  • 设计一个周期信号的波形识别及参数测量装置,该装置能够识别出给定信号的波形类型,并测量信号的参数。

    在这里插入图片描述

    周期信号波形识别及参数测量装置(J 题) 【高职高专组】--2021 年全国大学生电子设计竞赛

    一 任务

    设计一个周期信号的波形识别及参数测量装置,该装置能够识别出给定信号的波形类型,并测量信号的参数。

    二 要求

    1. 基本要求

    • (1)能够识别 1V≤VPP≤5V、100Hz≤ f ≤10kHz 范围内的正弦波、三角波和矩形波信号,并显示类型。
    • (2)能够测量并显示信号的频率 f,相对误差的绝对值不大于 1%。
    • (3)能够测量并显示信号的峰峰值 VPP,相对误差的绝对值不大于 1%。
    • (4)能够测量并显示矩形波信号的占空比 D,D 的范围为 20%~80%,绝对误差的绝对值不大于 2%。

    2. 发挥部分

    • (1)扩展识别和测量的范围。能够识别 50mV≤VPP≤10V、1Hz≤ f ≤50kHz 范围内的正弦波、三角波和矩形波信号,并显示类型。同时完成与基本部分(2)、(3)和(4)相同要求的参数测量。
    • (2)识别结果和所有测量参数同时显示,反应时间小于 3 秒。
    • (3)增加识别波形的类型不少于 3 种,增加测量参数不少于 3 个。
    • (4)其他。

    三 说明

    被测信号由函数发生器产生。测量精度以函数发生器输出显示为基准,测试时函数发生器自带。反应时间从函数发生器输出信号至装置时开始计时。

    四 评分标准

    在这里插入图片描述

    文件

    在这里插入图片描述
    在这里插入图片描述

    在这里插入图片描述

    展开全文
  • matlab开发-波形测量信号的参数识别。最佳窦的频率、振幅、相移和平均值与采样信号相匹配。
  • 对ADC采集到的数据进行分析,识别波形(正弦波,方波,三角波),通过串口发送识别结果,结构...这个方法已经被淘汰了,这种波形识别方法实在是不靠谱,我新上传了一个FFT的波形识别,比这个好多了,这个大家免费下载吧
  • 地质雷达波形识别方法论述.doc
  • 心电图中的各个波形都...所以识别这些波形以及提取相应特征对我们后续做心律失常的分类很重要。 我们在用算法做心律失常判别分类之前,有两个关键点: 第一步: 识别检测ECG信号中的波群(目前主要是先定位QRS波...

    心电图中的各个波形都包含了非常多的信息,例如RR间期可以反映心动周期的时限;相邻心动周期的 RR 间期的比值可以反映室性早搏;R 波和 S 波幅值的比值和 R 波和 S 波之间的时限可以反映房性早搏等异常情况,等等
    所以识别这些波形以及提取相应特征对我们后续做心律失常的分类很重要。

    我们在用算法做心律失常判别分类之前,有两个关键点:

    • 第一步: 识别检测ECG信号中的波群(目前主要是先定位QRS波群,再依次定位其它波群)
    • 第二步: 对波群进行信号特征的提取(不同波形的不同状态展示了心脏的情况,所以提取这些波群的信号特征,是我们做分类判别的关键)

    1.心电图波形

    首先来学习认识一下心电图中各个波形的含义
    心电图

    一个正常的心电信号在一个周期内,是由P波,QRS波群以及T波组成
    P波:代表心脏除极,一般呈现钝圆形,幅度约为0.25mV,持续时间为0.08~0.11s。
    PR间期:指心房除极开始到心室除极开始的传导时间,一般是从P波开始到QRS波的起点,正常PR间隔时间为:0.12s-0.20s。
    QRS:代表心室肌的除极产生的电位变化,是心电图中最高大,快速的波形。
    T波:代表心室肌的复极
    QT间期:代表心脏去极化和复极过程,即心室收缩的总时间。QT 间隔和心率相关,心率越快,QT 间隔越短,反之越长
    RR间隔:是指连续两个心电周期 R 峰值间隔变化特征,是常用的心拍识别标准之一

    2.心电信号的波形识别检测与特征提取

    心电信号的波形识别,主要是指识别QRS波群(因为它最明显)。只有当正确检测到QRS复合波群之后,我们才能根据QRS波群来确定其它典型波群的特征和位置,为心律失常分类提供基础。
    目前心电信号中QRS波群的检测主要有小波变换法,差分阈值法 等等 选哪个需要根据自己的方向来定,小波变换法的计算量较大。
    Pan-Tompkins算法是最经典的, 具体哪个算法最好,要根据自己的方向来定。因为这里面涉及一些信号处理的知识,自己需要先学学,目前暂时不能详细叙述各个波群检测算法的原理

    所以这里先待定填坑

    确定了QRS波群之后,我们可以根据QRS波群来确定其它波(T波,P波,QR间期等等)

    确定完这些波,我们就可以根据提取这些波的信号特征,为后期心律判别奠定基础
    心电信号特征提取的常用方法包括:心电信号的时域特征、心电信号的变换域特征等方法。。。
    心电信号的时域特征主要反映了心电信号的形态和直观特征,变换域特征是指分别从不同维度不同方向描绘心电信号,整合心电信号的时域特征和变换域特征就可以很好的描述心电信号啦。

    具体的特征提取方法还有待研究,这里先待定填坑

    ECG(心电)信号在波形检测完成之后会被分为多个心拍,不同的心拍类型应该被 分为特定的类别,这个过程就是心律失常的诊断和识别过程

    参考文献:
    可穿戴式心电监测模块的心律失常分类算法研究.卢莉莉
    基于 LSTM 的心律失常分类研究.李雪

    展开全文
  • 行业资料-电子功用-基于电流波形识别的MMC-HVDC直流线路单极接地故障保护方法
  • STM32F103通过AD采样后,根据RMS,分辨标准波形(三角波、方波、正弦波等)。开发环境为keil。
  • STM32周期波形信号识别和参数测量
  • 几篇关于心电信号分析的论文,包括降噪算法、特征点识别、波形识别等等。
  • 文章提出了一种新颖的卷积结构SincNet,直接从波形提取特征,作为说话人识别任务的输入。实验表明,SincNet在说话人辨认和说话人确认任务上都有性能提升。 论文地址: https://arxiv.org/abs/1808.00...

    说话人识别是从语音信号识别出说话者的任务,分为说话人辨认(speaker identification)和说话人确认(speaker verification)两类。文章提出了一种新颖的卷积结构SincNet,直接从波形提取特征,作为说话人识别任务的输入。实验表明,SincNet在说话人辨认和说话人确认任务上都有性能提升。

    论文地址:
    https://arxiv.org/abs/1808.00158
    代码地址:
    https://github.com/mravanelli/SincNet

    引言

    近年来,许多深度神经网络(DNNs)模型被用于说话人识别。过去大多数的尝试,都是基于手工设计的特征,例如FBank、MFCC等。这些特征在设计之初都是基于人类的听觉感知理论,并不能保证对于具体的语音任务都是最优的。因此,一些新的工作尝试将语音波形直接输入到CNN网络。
    本文的作者认为,CNN在处理原始语音波形时,起到关键作用的是第一层卷积层。第一层的卷积核可能会捕捉到一些人类直觉之外的,但是对神经网络有效的一些特征。基于这个想法,本文提出SincNet,将第一层卷积层设计为可训练的带通滤波器。实验表明SincNet相比于标准的CNN,收敛更快,性能更好。

    数据集

    本文提出的方法在不同的数据集上进行了验证,包括 TIMIT 和 Librispeech 数据集。TIMIT 包含462名说话人,Librispeech包含2484名说话人。在预处理时,切除掉语音开头和结尾的静音部分。Librispeech 中的长语音也进行分割,在超过125ms的静音段处进行切割。

    模型

    第一层卷积层的设计

    处理语音波形的第一层卷积,可以视为一组可训练的有限冲激响应滤波器(FIR),形式化描述如下:

    其中 x [ n ] x[n] x[n]是滑动窗口内的语音信号片段, h [ n ] h[n] h[n]是长度为 L L L的滤波器。在标准的CNN中, h [ n ] h[n] h[n]中所有的 L L L个元素都是从数据中学习的。在本文提出的SincNet中,将 h [ n ] h[n] h[n]预定义为一个函数 g g g g g g只具有少量可学习的参数 θ \theta θ。因此,前面的卷积公式修改如下:

    受到信号处理方法的启发,文章提出将 g g g定义为一个带通滤波器,因此 g g g就可以被描述成两个低通滤波器的结果的差分:

    其中 f 1 f_{1} f1 f 2 f_{2} f2 是可学习的参数,代表带通滤波器的低、高截止频率。上式是 g g g的频域表示,经过逆傅里叶变换,最终得到滤波器 g g g的时域表示:

    其中的 s i n c sinc sinc函数定义为:

    根据奈奎斯特采样定理, f f f应当不超过采样频率的一半。但是文章的作者指出并没有必要加入这一限制到网络设计中,因为他们发现, f f f经过训练后会很自然地符合这一规律。
    在传统信号处理的方法中,加窗操作被用来减弱频谱泄露效应,本文中也在卷积中加入了窗函数,因此加窗后的滤波器为:

    在本文中使用的窗函数是汉明窗,定义如下:

    模型整体结构

    诚如前文所述,文章的主要的贡献是对CNN的第一层卷积层进行改进。因此,在第一层卷积之后,使用了常见的用于说话人识别的网络结构。模型的整体架构如下:
    SincNet的整体结构

    实验

    说话人识别辨认

    本文在TIMIT和Librispeech数据集上训练了说话人辨认SincNet模型,并与基线系统进行比较。在不同数据集上,SincNet的表现均超过所有基线系统。
    说话人分类错误率(CER%)对比

    说话人确认

    文章还在Librispeech上进行说话人确认实验,分别比较了基于d-vector和基于DNN-class两类方法。可以看到,两类方法上,SincNet的性能都是最优的。
    说话人确认等错误率(EER%)对比

    结论

    本文提出了SincNet,一种新颖的处理时域波形的卷积网络结构。SincNet将第一层卷积作为可训练的FIR,使得网络的可解释性变得更强。SincNet的结构非常简洁,在实验中也表现出了比其它传统网络更快的收敛速度和更好的性能。SincNet是将信号处理概念融入到网络架构设计中的一次成功的尝试。


    在这里插入图片描述
    扫码识别关注,获取更多论文解读

    展开全文
  • 基于STM32F407和OV5640的视觉算法,当时在做全国大学生工程训练大赛,二维码识别采用的是正点原子的库;颜色识别自己写的算法,只识别红绿蓝,直接对RGB进行算法判定,不需要白平衡;色块追踪写来玩的,参考了其他人...
  • 信号的波形检测和判断 可以用于波形判断 以及检测
  • stm32f407 ad采集波形,da还原,接示波器显示,亲测可用
  • wave模块只支持非压缩的数据,因此可以忽略最后两个信息 params = f.getparams() [nchannels, sampwidth, framerate, nframes] = params[:4] # 读取波形数据 # 读取声音数据,传递一个参数指定需要读取的长度(以...
  • 脑电图波形分析和识别:频率、波幅、波形、位相、出现方式、出现部位 周期与频率 周期:指一个波从开始到终止的时间,即从一个波底(波顶)到下一个波低(波顶)所需要的时间,用ms表示。 频率:同一周期的脑波在...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 15,445
精华内容 6,178
关键字:

波形识别

友情链接: assxxiattve.zip