Discrete Wavelet Transform - Visualisasi Hubungan antara Koefisien Detail Terurai dan Sinyal

12

Saya mencoba untuk secara langsung memvisualisasikan hubungan antara DWT (detail discrete wavelet transform) dan sinyal asli / rekonstruksinya. Tujuannya adalah untuk menunjukkan hubungan mereka secara intuitif. Saya ingin bertanya (lihat pertanyaan di bawah): jika ide dan proses yang saya buat sudah benar sejauh ini, dan jika saya benar mungkin akan lebih baik mengurangi perkiraan tingkat 1 dari sinyal asli sebelum memvisualisasikan hubungan mereka .

Contoh minimal

Berikut contoh minimal saya mendasarkan penjelasan saya pada, menggunakan ECG data contoh dari Pythonpywavelets , yang memiliki 1024 nilai, sebagai sederhana 1D sinyal:

import pywt
import pywt.data
import numpy as np
import matplotlib.pyplot as plt

x = pywt.data.ecg()
plt.plot(x)
plt.legend(['Original signal'])

Sinyal asli

Dekomposisi dilakukan menggunakan Symmlet 5 dengan total 6 level:

w = pywt.Wavelet('sym5')
plt.plot(w.dec_lo)
coeffs = pywt.wavedec(x, w, level=6)

(Lossy) rekonstruksi sinyal berfungsi seperti yang diharapkan ketika sengaja meninggalkan koefisien detail tingkat yang lebih tinggi (sinyal diplot pada skala x seragam [0,1] untuk kenyamanan):

def reconstruction_plot(yyy, **kwargs):
    """Plot signal vector on x [0,1] independently of amount of values it contains."""
    plt.plot(np.linspace(0, 1, len(yyy)), yyy, **kwargs)

reconstruction_plot(pywt.waverec(coeffs, w)) # full reconstruction 
#reconstruction_plot(pywt.waverec(coeffs[:-1] + [None] * 1, w)) # leaving out detail coefficients up to lvl 5
#reconstruction_plot(pywt.waverec(coeffs[:-2] + [None] * 2, w)) # leaving out detail coefficients up to lvl 4
#reconstruction_plot(pywt.waverec(coeffs[:-3] + [None] * 3, w)) # leaving out detail coefficients up to lvl 3
reconstruction_plot(pywt.waverec(coeffs[:-4] + [None] * 4, w)) # leaving out detail coefficients up to lvl 2
#reconstruction_plot(pywt.waverec(coeffs[:-5] + [None] * 5, w)) # leaving out detail coefficients up to lvl 1
reconstruction_plot(pywt.waverec(coeffs[:-6] + [None] * 6, w)) # leaving out all detail coefficients = reconstruction using lvl1 approximation only
plt.legend(['Full reconstruction', 'Reconstruction using detail coefficients lvl 1+2', 'Reconstruction using lvl 1 approximation only'])

Sinyal yang direkonstruksi

DWT di atas menghasilkan vektor aproksimasi level 1 dari 24 nilai, vektor koefisien detail level 1 dari 24 nilai, vektor detail level 2 dari 40 nilai, level 3 dari 72 nilai, level 4 dari 135 nilai, level 5 dari 262 nilai, dan level 6 dari 516 nilai:

plt.stem(coeffs[1]); plt.legend(['Lvl 1 detail coefficients'])
plt.stem(coeffs[2]); plt.legend(['Lvl 2 detail coefficients'])
plt.stem(coeffs[3]); plt.legend(['Lvl 3 detail coefficients'])
plt.stem(coeffs[4]); plt.legend(['Lvl 4 detail coefficients'])
plt.stem(coeffs[5]); plt.legend(['Lvl 5 detail coefficients'])
plt.stem(coeffs[6]); plt.legend(['Lvl 6 detail coefficients'])

Koefisien detail Level 1 Koefisien detail Level 2 Koefisien detail Level 3 Koefisien detail Level 4 Koefisien detail Level 5 Koefisien detail Level 6

Tampaknya kita melihat pola yang jelas di sekitar lonjakan sinyal asli (juga memperhatikan skala plot di atas).

Sekarang untuk pertanyaan saya:

  1. Benarkah kita dapat secara langsung menghubungkan koefisien tersebut dengan sinyal? Amplitudo dari koefisien sesuai dengan amplitudo yang dengannya wavelet terjadi pada sinyal (sumbu y), dan posisi koefisien sesuai dengan waktu (sumbu x). Atau ada sesuatu di antara kita perlu dipertimbangkan?
  2. Setelah DWT perkiraan lvl1 akhir tetap. Apakah masuk akal untuk tidak memvisualisasikan hubungan koefisien detail dengan sinyal asli, tetapi sebaliknya dengan sinyal asli minus perkiraan lvl1? (Saya tahu bahwa saya kemungkinan besar juga akan melihat hubungan antara koefisien dan sinyal tanpa melakukan ini, lihat misalnya plot di bawah ini. Hanya untuk ini masuk akal atau tidak. Jika masuk akal untuk koefisien detail lvl1 maka mungkin juga masuk akal untuk lvl2 detail koefisien untuk dibandingkan dengan sinyal asli minus perkiraan lvl2, kan?). Sebuah contoh:

    # Reconstruction of signal using just lvl1 approximation
    approx_lvl1 = pywt.waverec(coeffs[:-6] + [None] * 6, w)
    # interpolate to original amount of samples (necessary due to numeric solution of transformation not yielding same amount of values)
    approx_lvl1_interp = np.interp(x=np.arange(0, 1024), xp=np.linspace(0, 1024, len(approx_lvl1)), fp=approx_lvl1)
    x_without_lvl1approx = x - approx_lvl1_interp
    
  3. Visualisasi langsung dari hubungan antara koefisien detail dan sinyal I hanya menggunakan plot baik sinyal dan koefisien pada sumbu x [0,1]. Secara konseptual ini harus valid, tetapi saya tidak yakin apakah saya benar-benar membutuhkan offset terhadap margin (mis. Koefisien vektor pertama dan terakhir tidak diposisikan di awal atau akhir sinyal):

    def reconstruction_stem(yyy, **kwargs):
        """Plot coefficient vector on x [0,1] independently of amount of values it contains."""
        plt.stem(np.linspace(0, 1, len(yyy)), yyy, **kwargs)
    
    reconstruction_plot(x, color='orange')
    reconstruction_plot(x_without_lvl1approx, color='red')
    reconstruction_stem(coeffs[1])
    plt.legend(['Original signal', 'Original signal - lvl1 approximation', 'Detail coefficients'])
    

Hubungan antara koefisien detail lvl1 dan sinyal Hubungan antara koefisien detail lvl2 dan sinyal Hubungan antara koefisien detail lvl3 dan sinyal Hubungan antara koefisien detail lvl4 dan sinyal Hubungan antara koefisien detail lvl5 dan sinyal Hubungan antara koefisien detail lvl6 dan sinyal

Apakah ada penjelasan intuitif untuk koefisien kuat yang tidak secara langsung pada posisi puncak dalam data asli (misalnya pada level 1 yang terendah (negatif terkuat) di sekitar 0,25, serta yang tertinggi (positif terkuat) sekitar 0,75 )? Meskipun ada pola yang jelas (lag positif + amplitudo negatif, lag negatif + amplitudo positif) yang tampaknya agak "jauh" bagi saya. Tapi mungkin ada penjelasan yang bagus untuk itu.

Terimakasih telah menjawab!

geekoverdosis
sumber
Anda tidak mendapatkan jawaban, tetapi pertanyaan Anda sendiri adalah tutorial yang bagus untuk menerapkan analisis wavelet dengan Python. Terima kasih!
Farzad

Jawaban:

1

Penting untuk membedakan dengan jelas antara koefisien pendekatan dan detail pada setiap tingkat dekomposisi dan tingkat yang terkait.

CD86
sumber
0

Saya baru sekarang mulai mencoba-coba dengan wavelet, dan saya masih berjuang bahkan dengan pertanyaan yang sangat mendasar seperti "bagaimana seseorang memilih dari kumpulan wavelet yang tersedia" (mungkin ada hubungannya dengan jumlah level yang Anda butuhkan untuk mencapai "cukup baik" representasi), dan "apa semua kehebohan tentang denoising dengan wavelet", karena saya tampaknya dapat mencapai hasil yang lebih baik untuk tipe data saya dengan denoising gaussian lurus atau filter median. Tapi saya ngelantur ....

Satu hal yang saya catat di atas adalah bahwa penomoran level Anda tampaknya tidak konsisten dengan apa yang saya yakini sebagai konvensi wavelet biasa. Khususnya koefisien [0] adalah amplitudo aproksimasi pada tingkat terakhir, dalam kasus Anda 6 koefisien [1] adalah amplitudo detail di level 6 koefisien [2] adalah amplitudo detail di level 5 ... koefisien [6] adalah detail amplitudo pada level 1

Jadi rekonstruksi Anda hanya dari level 5 dan 6, bukan level 1 dan 2 seperti yang ditunjukkan dalam plot Anda.

=========

Pembaruan: Saya lebih mengacaukan kode Anda, dan saya pikir ide Anda untuk menggambarkan korelasi antara koefisien dan fitur sinyal adalah suara, tetapi tidak sempurna. Saya telah sedikit berkeliaran dengan kode Anda untuk menggambarkan ini lebih baik, lihat di bawah. Perhatikan bahwa pada setiap langkah saya skala koefisien untuk besarnya sinyal. Ini memungkinkan seseorang untuk berbicara tentang konsep thresholding juga.

import pywt
import pywt.data
import numpy as np
import matplotlib.pyplot as plt

plt.close('all')

def reconstruction_plot(yyy, **kwargs):
    """Plot signal vector on x [0,1] independently of amount of values it contains."""
    #plt.figure()
    #plt.plot(np.linspace(0, 1, len(yyy)), yyy, **kwargs)
    ym = np.median(yyy)
    plt.plot(np.linspace(0, 1., num=len(yyy)), yyy-ym, **kwargs)


def reconstruction_stem(yyy, xmax, **kwargs):
    """Plot coefficient vector on x [0,1] independently of amount of values it contains."""
    ymax = yyy.max()
    plt.stem(np.linspace(0, 1., num=len(yyy)), yyy*(xmax/ymax), **kwargs)


x = pywt.data.ecg()
w = pywt.Wavelet('sym5')
nl = 6
coeffs = pywt.wavedec(x, w, level=nl)


'''
plt.figure()
plt.stem(coeffs[1]); plt.legend(['Lvl 6 detail coefficients'])
plt.figure()
plt.stem(coeffs[2]); plt.legend(['Lvl 5 detail coefficients'])
plt.figure()
plt.stem(coeffs[3]); plt.legend(['Lvl 4 detail coefficients'])
plt.figure()
plt.stem(coeffs[4]); plt.legend(['Lvl 3 detail coefficients'])
plt.figure()
plt.stem(coeffs[5]); plt.legend(['Lvl 2 detail coefficients'])
plt.figure()
plt.stem(coeffs[6]); plt.legend(['Lvl 1 detail coefficients'])
'''


xmax = x.max()
for i in range(nl):
    plt.figure()
    reconstruction_plot(x) # original signal 
    #reconstruction_plot(pywt.waverec(coeffs, w)) # full reconstruction 
    reconstruction_plot(pywt.waverec(coeffs[:i+2] + [None] * (nl-i-1), w)) # partial reconstruction 
    reconstruction_stem(coeffs[i+1], xmax, markerfmt ='none', linefmt='r-')
    #plt.legend(['Original', 'Full reconstruction', ('Rec to lvl %d')%(nl-i), ('Details for lvl %d')%(nl-i)])
    plt.legend(['Original', ('Rec to lvl %d')%(nl-i), ('Details for lvl %d')%(nl-i)])
pengguna40719
sumber