问题描述
我想获得Matlab中两个数据集之间的样本偏移(使它们及时同步),这是一个很常见的问题.因此,我使用互相关函数xcorr或互协方差函数xcov(在大多数情况下,两者都提供相似的结果).使用人工数据,它可以很好地工作,但是我对真实"数据感到吃力,尽管它应该几乎相同. Matlab总是说偏移量将为零.我正在使用这段简单的代码:
I want to get the offset in samples between two datasets in Matlab (getting them synced in time), a quite common issue. Therefore I use the cross correlation function xcorr or the cross covariance function xcov (both provide similar results in most cases for this purpose). With artificial data it works fine, but I struggle with "real" data, even though it should be pretty much the same. Matlab always says the offset would be zero. I'm using this simple piece of code:
[crossCorr] = xcov(b, c);
[~, peakIndex] = max(crossCorr())
offset = peakIndex - length(b)
我在pastebin上发布了一个完全可运行的示例m文件,其中的数据摘录经过了降采样:在pastebin上包含数据的代码
I've posted a fully runable example m-file with a downsampled data excerpt on pastebin:Code with data on pastebin
降采样的摘录似乎并不完全适合评估效果. 这里是原始频率更大的样本,请改用此样本一个>.不幸的是,它对于pastebin来说太大了.
The downsampled excerpt seems to be not fully suitable for evaluating the effect. Here's a much larger sample with the original frequency, pease use this one instead. Unfortunately it was too big for pastebin.
如该图所示,通过交叉协方差获得偏移应该完全没有问题.为了避免数值问题,我还尝试将数据更好地缩放,但这一点都没有改变.
As the plot shows it should be no problem at all to get the offset via cross covariance. I also tried to scale the data nicer in order to avoid numerical problems, but that didn't change anything at all.
如果有人可以告诉我我的错误,那将很棒.
Would be great if someone could tell me my mistake.
推荐答案
原则上您的方法没有错,我成功地使用了完全相同的方法来临时对齐同一信号的不同音频记录.
There's nothing wrong with your method in principle, I used exactly the same approach successfully for temporally aligning different audio recordings of the same signal.
但是,似乎对于您的时间序列而言,相关性(或协方差)根本不是比较移位版本的正确方法-可能是因为它们所包含的时间比例与总长度相当.一种替代方法是使用残差方差,即,移位版本之间的差异的方差.这是这个想法的实现(不是特别优雅):
However, it appears that for your time series, correlation (or covariance) is simply not the right measure to compare shifted versions – possibly because they contain components of a time scale comparable to the total length. An alternative is to use residual variance, i.e. the variance of the difference between shifted versions. Here is a (not particularly elegant) implementation of this idea:
lags = -1000 : 1000;
v = nan(size(lags));
for i = 1 : numel(lags)
lag = lags(i);
if lag >= 0
v(i) = var(b(1 + lag : end) - c(1 : end - lag));
else
v(i) = var(b(1 : end + lag) - c(1 - lag : end));
end
end
[~, ind] = min(v);
minlag = lags(ind);
对于您的(较长)数据集,结果为minlag = 169
.绘制滞后的剩余方差可以得出:
For your (longer) data set, this results in minlag = 169
. Plotting residual variance over lags gives:
这篇关于Matlab:使用交叉协方差对齐数据的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!