iT邦幫忙

2022 iThome 鐵人賽

DAY 27
0

為何會使用時頻譜?

在穿戴式裝置資料分析中,擁有多種不同的訊號,如:裝置中會設置加速度計、陀螺儀等,則會紀錄多軸加速度數值和旋轉的角度數值,而肌電圖則會紀錄多個通道(channel)的數值。除了站在時域的角度,使用原始的時序訊號進行分析之外,亦有許多學者會將資料轉換至頻域的角度,使用傅立葉轉換、小波轉換等轉換資料。其中時頻譜(Spectrogram),又稱聲譜圖,為其中一種常見的頻域分析手段,是一種描述訊號中各個頻率會如何隨著時間變化的熱圖。

時頻譜

在傳統的頻域分析,會使用傅立葉轉換來將資料轉換成2維的頻譜,可以將訊號分解成多個不同頻率和振幅的週期波,但並不包含時間變化的資訊。因此若要保有時間的變動以及頻率的分佈,則會使用到短時距傅立葉轉換(time-dependent Fourier transform, STFT),為了要呈現3維的資訊,因此則會使用熱圖來表現。

短時距傅立葉轉換

在一連串訊號中,資料會根據設定的window大小被切割成數個window,而這些window常常會有重疊的部分,以用來避免切割後會造成邊界上的誤差。
每個window各自進行傅立葉轉換,對轉換後得到的複數結果進行相加後,即可得到每一個時間點時間上頻率、振幅的變化。
而為了追求更快的運算速度,在大多數的計算會使用快速傅立葉轉換來進行。
https://ithelp.ithome.com.tw/upload/images/20221005/20151279A3KoZJRlem.png
圖片來源:連結

短時距傅立葉轉換優缺點

優點:相較於傅立葉轉換,更能在頻域上觀察頻率隨著時間的變化
缺點:運算相較於其他轉換複雜許多

實作

本示範使用Day2的資料集介紹中的第二個資料集作為示範

import pandas as pd
import numpy as np
%matplotlib inline
# 讀檔
EMG_0 = pd.read_csv('./archive/0.csv',header=None)
EMG_1 = pd.read_csv('./archive/1.csv',header=None)
EMG_2 = pd.read_csv('./archive/2.csv',header=None)
EMG_3 = pd.read_csv('./archive/3.csv',header=None)
# 每個動作持續20秒,共紀錄6次
# 一筆資料代表40ms = 0.04 s 
# 由於原始資料並沒有將每次紀錄切段,因此先根據資料集敘述進行資料切分
# 為了避免資料片段過少,因此決定嘗試以每5秒作為一片段,來作為嘗試,因此一個片段會包含125筆資料
segment = np.array([range(1,24)])
EMG_0 = EMG_0.iloc[0:2875,:]
EMG_0['segment'] = np.repeat(segment,[125])
EMG_1 = EMG_1.iloc[0:2875,:]
EMG_1['segment'] = np.repeat(segment,[125])
EMG_2 = EMG_2.iloc[0:2875,:]
EMG_2['segment'] = np.repeat(segment,[125])
EMG_3 = EMG_3.iloc[0:2875,:]
EMG_3['segment'] = np.repeat(segment,[125])

EMG_total = pd.concat([EMG_0, EMG_1, EMG_2, EMG_3]) ## 合併多個dataframe
EMG_total.columns = ["channel%02d" %i for i in range(1,65)]+['gesture','segment'] ## 重新命名column name

https://ithelp.ithome.com.tw/upload/images/20221005/20151279fZEoczBvyq.png

from scipy import signal
from scipy.fft import fftshift
import matplotlib.pyplot as plt
freq, times, spectrogram = signal.spectrogram(EMG_total.iloc[:,0], fs=25)
plt.figure(figsize = (7,25))
plt.pcolormesh(times, freq, spectrogram)
plt.imshow(spectrogram)
plt.ylabel('Frequency [Hz]')
plt.xlabel('Time [sec]')
plt.show()

https://ithelp.ithome.com.tw/upload/images/20221005/20151279Cg1C5ueK3s.png


上一篇
[Day26] Overfitting and Underfitting
下一篇
[Day 28] 3D CNN
系列文
人類行為數據分析- 以R和Python進行實作30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言