Sonnerie à valeur réelle lors du remplissage nul FFT de longueur impaire

13

J'essaie donc d'écrire un interpolateur dans le domaine fréquentiel qui met à zéro la réponse en fréquence d'un signal et les transformations inverses. Il y a deux cas que je dois traiter:

  1. Réponse de longueur égale - il faut diviser le bac car il est ambigu. Je copie donc la partie négative du spectre et ajoute des zéros entre les deux.Fs/2n*(interp-1)-1
  2. Réponse de longueur impaire - il n'y a pas de bac il suffit donc de diviser la fréquence positive / négative et d'insérer des zéros entre eux.Fs/2n*(interp-1)

Le code qui fait le zéro-padding peut être vu ici

// Copy negative frequency components to end of buffer and zero out middle
//  inp    - input buffer of complex floats
//    n    - transform size
//  interp - interpolation amount
void zero_pad_freq(cfloat_t *inp, size_t n, size_t interp) {
    if ((n % 2) == 0) {
        memmove(inp + n*interp - n/2, inp + n/2,     n/2*sizeof(cfloat_t));
        memset (inp + n/2 + 1, 0,       (n*(interp-1)-1)*sizeof(cfloat_t)); // Duplicate Fs/2 so we need one less zero

        inp[n/2]          /= 2.0;
        inp[n*interp-n/2] /= 2.0;
    } else {
        memmove(inp + n*interp - n/2, inp + (n+1)/2, n/2*sizeof(cfloat_t));
        memset (inp + (n+1)/2, 0,         (n*(interp-1))*sizeof(cfloat_t));
    }
}

Le premier cas fonctionne bien, je teste sur un signal chirp et interpole très bien, il y a un peu de bruit numérique, mais il est rond déclenché par une FFT Que pouvez - vous faire (premier ou si du signal spectacle):50μs

50μs

Le canal imaginaire a une petite ondulation, mais pas aussi mauvais:

Fs/2Fs/2

gct
la source
Vos parcelles sont un peu difficiles à voir car elles ont été réduites.
Jason R du
@Jason désolé, je pensais qu'ils étaient liés, j'ai peaufiné le code html pour qu'ils puissent cliquer maintenant en taille réelle.
gct
3
Avez-vous un code ou un fichier d'exemple pour ce que vous utilisez comme entrée? Une chose à garder à l'esprit est que les conditions aux limites assumées par la DFT. Plus précisément, il existe une hypothèse inhérente que le signal d'intérêt est périodique. Donc, s'il y a une discontinuité entre le premier et le dernier échantillon dans l'entrée de longueur impaire, alors vous pouvez voir sonner comme ce que vous avez observé. Il est possible que l'échantillon de longueur paire soit plus continu du début à la fin, de sorte que vous ne voyez pas ce phénomène.
Jason R
Je n'ai pas de données dans un format que n'importe qui d'autre pourrait facilement digérer, mais je pense que vous avez raison. Je viens juste de travailler et j'ai recompilé mon code / régénéré une entrée de test (gazouillement 10Hz-100Hz sur 1 seconde) et relancé le code et je n'ai pas eu la sonnerie. J'ai vu votre commentaire et changé la fréquence en 10-100.314 et je vois maintenant la sonnerie sur les transformations paires et impaires.
gct
1
Avez-vous essayé d'appliquer une fonction de fenêtre à vos données? Cela réduira normalement la sonnerie.
MarkSci

Réponses:

1

En mettant à zéro les bacs haute fréquence, vous avez effectivement multiplié le spectre du signal avec une fonction rectangulaire. La multiplication en fréquence est une convolution dans le temps et la paire de Fourier d'un rect est un sinc. Donc, ce que vous avez vraiment fait, c'est convoluer le signal du domaine temporel avec un sinc avec la largeur du lobe principal du sinc inversement proportionnelle à la longueur du rect. C'est pourquoi les nombreuses techniques de conception de filtres comme la conception de Parks-McClellan dans ce qu'on appelle une bande de "région de transition" ou de "transition" afin qu'il n'y ait pas de changement instantané de la réponse en fréquence du filtre. Ces techniques de conception de filtres sont importantes car le filtre "idéal" comme vous l'avez utilisé a de tels effets indésirables dans le domaine temporel.

user27575
la source
0

Une étape dans le domaine fréquentiel apparaîtra comme des ondulations dans le domaine temporel. Si vous lissez vos données de fréquence avec une fonction de fenêtre (par exemple une fenêtre de Hamming), cela devrait réduire considérablement les ondulations.

Jian
la source