动态时间规整算法——DTW
没有做过机器学习的小伙伴们对这个算法应该不是特别的了解,因为机器学习经常会用到这个算法。再将这个算法之前,我们先看一下初中的知识点。
欧几里得距离
在讲解动态时间规整算法(Dynamic Time Warping, DTW)之前,我们先来了解一下,在日常生活中,用来计算两点的距离,我们是怎么进行的。回想一下初中的数学知识点——几何距离,如下图所示的二维空间中计算A点到B点的距离。
其中A点和B点的坐标分别为:A(1,2) 和 B(2,1),如果要算A点到B点的距离,那么计算方式为:
如果是在三维的空间,如下图所示:
其中A点和B点的坐标分别为:A(0,1,2) 和 B(1,3,1),如果要算A点到B点的距离,那么计算方式为:
以此类推,对于n维的空间,距离公式应该表达为:
从初中用到现在,那么你知道这个和计算距离的方法是谁发明的吗?(应该不是我嘿嘿嘿~~)。发明这个方法的大神就是欧几里得,计算的距离公式也叫做欧几里得距离,简称欧氏距离。
你会好奇,无端端讲了欧几里得距离做什么,我们先不急,继续往下看。
动态时间规整
上面我们讲到了欧几里得距离,举的两个例子也是针对空间上的位置计算,那么如果现在是两个时序信号呢,也就是加上了时间维度,这种计算是否还能够成立,接下来我们来看一下一个小例子,如下图所示,假设用户A和用户B两个人在读 “我爱中国”。用户A说的比较干脆,用户B说的有点拖音(即用户A说:“我爱中国”,用户B说“我~爱中国”,差别就是用户B在说我的时候拖了一下音)。我们假设用户A的发音是【1,2,1,3】,用户B的发音是【1,1,2,1,3】,两个用户的发音区别就是用户B在说第一个字的时候拖了音,如下图所示:
因为用户A和用户B讲的是同一句话,并且意思也是一样的,那么按照机器学习理论来说,它们的相似性应该很相似,也就是距离很近,OK,那如果我们认为是n维数据,然后使用n维的欧氏距离来计算一下这两者的距离,表达式为:
通过上面表达式计算得知,用户A和用户B的距离为:
这也太远了吧。不是说相似吗。
细心的你已经发现了一个问题,欧几里得距离的计算方式是运用在空间上的比较多。对于时间序列,欧几里得距离计算方法好像显得不那么友好了。所以为了解决这个问题,日本的一位学者 Itakura 在60年代提出了动态时间规整算法(Dynamic Time Warping,DTW),用于衡量两个长度不同的时间序列的相似度。把未知量伸长或缩短(压扩),直到与参考模板的长度一致,在这一过程中,未知序列会产生扭曲或弯折,以便其特征量与标准模式对应。具体做法如下图所示:
图中的红线就是将用户B的语音序列和用户A的语音序列对应起来,实现时间规整的思想,这样计算的距离才会是最短的。
那么DTW算法的步骤如下:
计算两个序列各个点之间的距离矩阵;
寻找一条从矩阵左上角到右下角的路径,使得路径上的元素和最小:
我们称路径上的元素之和为路径的长度,那么怎么去寻找长度最小的路径呢?
矩阵从左上角到右下角的路径长度有以下性质:
(1) 当前的路径长度 = 前一步的路径长度 + 当前元素的大小
(2) 路径上的某个元素(i,j),它的前一个元素只可能为以下三者之一:
a. 左边的相邻元素(i, j-1)
b. 上面的相邻元素(i-1, j)
c. 左上方的相邻元素(i-1, j-1)
表达式表示为:
3. 寻找到最后的右下角就是路径的最小路径。
接下来,我们来对用户A和用户B进行动态时间规整步骤的解析:
首先,将序列A和序列B的矩阵列举出来,然后元素两两相减:
通过相减后得到上面的一个矩阵,接下来就定义一个结果矩阵来存放路径的长度,如下图所示,初始化结果矩阵,然后计算最上面一行和最左边一列的路径和,因为根据上面公式得到,第一行的每一个节点i只能从它的左边i-1过来,而每一列的每一个节点j只能从它的上一个节点j-1过来。然后再计算其他的路径,根据公式,在其他的节点中(i,j)的路径前一个点有三个(i,j-1)、(i-1,j-1)、(i-1,j),分别计算取最小值作为当前的数值。依次计算遍历。
最后得到的结果矩阵为:
最右下角的元素数值就是用户A和用户B两个序列的距离,结果为0,说明用户A和用户B所说的话是一样的。
DTW的代码如下:
#include<iostream>
#include<string.h>
#include<stdlib.h>
using namespace std;
#define NUM1 6 //序列中样本点的个数简单起见,假设2个序列的样本点一样多
#define NUM2 5
#define max 999
#define Min(a,b) (a<b?a:b)int main()
{int i,j,k;//int a[NUM1],b[NUM2];int b[4]={1,2,1,3};int a[6]={1,1,2,1,3};int distance[NUM1+1][NUM2+1];int output[NUM1+1][NUM2+1];memset(distance,0,sizeof(distance));memset(output,0,sizeof(output));for(i=0;i<=NUM1;i++){for(j=0;j<=NUM2;j++){distance[i][j]=max;output[i][j]=max;}}distance[0][0]=0;output[0][0]=0;//for(i=0;i<NUM1;i++) cin>>a[i];//for(i=0;i<NUM2;i++) cin>>b[i];for(i=1;i<=NUM1;i++)for(j=1;j<=NUM2;j++)distance[i][j]=abs(b[j-1]-a[i-1]); //计算点与点之间的欧式距离for(i=1;i<NUM1;i++){for(j=1;j<NUM2;j++)cout<<distance[i][j]<<'\t';cout<<endl;} //输出整个欧式距离的矩阵cout<<endl;for(i=1;i<NUM1;i++)for(j=1;j<NUM2;j++) output[i][j]=Min ( Min(output[i-1][j-1],output[i][j-1]) ,output[i-1][j] )+distance[i][j];//DP过程,计算DTW距离for(i=1;i<NUM1;i++){for(j=1;j<NUM2;j++)cout<<output[i][j]<<'\t';cout<<endl;} //输出最后的DTW距离矩阵,其中output[NUM][NUM]为最终的DTW距离和system("pause");return 0;
}
结果输出为:
动态时间规整算法——DTW相关推荐
- 基于动态时间规整算法(DTW)的语音识别技术研究-含Matlab代码
⭕⭕ 目 录 ⭕⭕ ⏩ 一.引言 ⏩ 二.动态时间规整算法基本原理 ⏩ 三.语音识别实例分析 ⏩ 四.参考文献 ⏩ 五.Matlab代码获取 ⏩ 一.引言 在语音识别技术的发展过程中,动态时间规整算法 ...
- 动态时间规整算法DTW
动态时间规整算法(dynamic time warping,DTW),最早由日本学者Itakura提出,用于衡量两个时间序列的相似度,也可用于将多个测试序列与标准序列对齐,从而实现序列长度的归一化. ...
- 动态时间规整算法(Dynamic Time Warping, DTW)之初探单词语音识别
动态时间规整算法(DTW)是最近接触的一种提取时间序列模板方法.本文主要是一些自己的学习记录,并适当地加入自己的理解.若有见解不一致之处,欢迎交流. 1 动态时间规整(DTW)基本思想 先从单词语音时 ...
- DTW动态时间规整算法
原文地址:https://blog.csdn.net/qcyfred/article/details/53824507 https://zhuanlan.zhihu.com/p/43247215 动态 ...
- 动态时间规整算法(DTW)通俗易懂
动态时间规整算法(Dynamic Time Warping ) 来源: -假定一个孤立词识别系统,利用模板匹配法进行识别.训练阶段,用户将词汇表种每一个词都念一遍,将其特征矢量的时间序列作为模板(te ...
- 【时序】动态时间规整(DTW)算法原理及Python实现
DTW 简介 DTW 定义 动态时间规整(Dynamic Time Warping,DTW)用于比较具有不同长度的两个阵列或时间序列之间的相似性或距离. 假设要计算两个等长数组的距离: a = [1, ...
- 动态时间规整算法: 从DTW到FastDTW
目录 动态时间规整算法: 从DTW到FastDTW 总结: 简介[^1] DTW[^1] FastDTW:使用多级粗化的方法[^1] 结果 动态时间规整算法: 从DTW到FastDTW 总结: Fas ...
- 崔岩的笔记——动态时间规整算法(Dynamic Time Warping,DTW)
什么是动态时间规整算法,他是用来干什么的 用于两个时间不同的特征序列的相似度比较. 举个例子:该算法最早的应用对象是语音识别,通过进行数据库语音特征和说话语音特征的相似度比较进行语音识别,但每个人说话 ...
- 语音信号处理之(一)动态时间规整(DTW)
语音信号处理之(一)动态时间规整(DTW) zouxy09@qq.com http://blog.csdn.net/zouxy09 这学期有<语音信号处理>这门课,快考试了,所以也要了解了 ...
最新文章
- ActiveMQ_Linux安装(一)
- 版本控制入门-----搬进Github
- 【PAT甲级 一个字符数组是否被另一个包含】1092 To Buy or Not to Buy (20 分) C++
- java必知必会_Java构造器必知必会
- java地址传递_关于java中是地址传递还是值传递的测试
- 全排列问题(洛谷P1706题题解,Java语言描述)
- C++ 接口继承与实现继承的区别和选择
- 知识图谱研讨实录09丨肖仰华教授带你读懂知识图谱语言认知
- [渝粤教育] 广东-国家-开放大学 21秋期末考试物权法10774k1
- Shell中的变量替换
- 安卓课设:翻译君APP(附开源地址)
- visionman-visionpro培训大纲
- SSM车辆维修管理系统毕业设计总结篇
- 计算机用户界面的设计,计算机软件用户界面设计的基本原则
- 写出linux命令的功能,练习一LINUX命令测试题1
- 全国青少年软件编程(Scratch)一级2019考试测试卷最后一道编程题!
- RStudio用不了怎么办?
- 编写各种outofmemory/stackoverflow程序
- 苹果9是5g手机吗_苹果手机可以量体温?这是真的吗
- pdc是什么部门_PDC和BDC_部署_迁移
热门文章
- 电脑垃圾,怎么清理电脑垃圾 让电脑全面瘦身
- 借助ADB冻结与卸载Android系统应用(免ROOT)
- hightcharts-vue 蜡烛图 股票绘图 candlestick
- 4.试用期个人工作总结(篇四)
- HAUT 1262 魔法宝石 (最短路变形 or 暴力)
- backface-visibility
- linux 内核进程与用户进程的通信 方法一 使用sockopt与内核交换数据
- 任天堂游戏服务器系统,买个服务器当电脑主机如何确保买到新版任天堂Switch游戏主机?...
- 编译linux源码报错,记录一次Linux内核源码编译实验
- IDC报告出炉,ZDNS连续五年DDI领域市场占有率第一