Convolución lineal usando C y MATLAB

Un concepto clave que a menudo se presenta a quienes se dedican a la ingeniería electrónica es la convolución lineal. Este es un componente crucial del procesamiento de señales digitales y señales y sistemas . Teniendo en cuenta el interés general y las implicaciones académicas, este artículo presenta el concepto y sus aplicaciones y lo implementa utilizando C y MATLAB .

Convolución: cuando se habla puramente matemáticamente, la convolución es el proceso mediante el cual se puede calcular la superposición de dos gráficos. De hecho, la convolución también se interpreta como el área compartida por los dos gráficos a lo largo del tiempo. Metafóricamente, es una mezcla entre las dos funciones cuando una pasa sobre la otra. Entonces, dadas dos funciones F(n) y G(n), la convolución de las dos se expresa y viene dada por la siguiente expresión matemática:

f(t)*g(t)=\int_{-\infty }^{\infty} f(u).g(t-u)du

o

f(n)*g(n)=\sum_{k=-\infty}^{\infty} f(k).g(n-k)

Linear convolution

Entonces, claramente intuitivo como parece, debemos tener en cuenta el TIEMPO. La convolución implica funciones que se mezclan con el tiempo. Esto se introduce en la expresión usando el cambio de tiempo, es decir, g(tu) es g(t) desplazado a la derecha ‘u’ veces). Además, cómo caracterizamos este tiempo también es importante. Antes de continuar, recopilemos los requisitos previos involucrados:

  • Funciones: Matemáticamente, miramos funciones o gráficos. Sin embargo, es importante tener en cuenta que el equivalente práctico aquí es una Señal. Nos ocupamos de la convolución de 2 señales.
  • Sistemas LTI: Los sistemas lineales invariantes en el tiempo son sistemas o procesos que producen una salida lineal e invariante en el tiempo, es decir, la salida satisface la linealidad (regla de superposición) y no cambia con el tiempo. La convolución es la relación entre la entrada y la salida de un sistema LTI.
  • Respuesta de impulso: una respuesta de impulso es lo que normalmente se obtiene si el sistema en cuestión está sujeto a una señal de dominio de tiempo de corta duración. Diferentes sistemas LTI tienen diferentes respuestas de impulso.
  • Sistema de tiempo: podemos usar señales de tiempo continuo o señales de tiempo discreto . Se supone que los lectores conocen y entienden la diferencia. La convolución se puede definir para señales CT y DT.

Convolución lineal: la convolución lineal es un medio por el cual uno puede relacionar la salida y la entrada de un sistema LTI dada la respuesta de impulso del sistema. Claramente, se requiere convolucionar la señal de entrada con la respuesta de impulso del sistema. Usando la expresión anterior, se puede formar la siguiente ecuación:

f(n)*h(n) = \sum_{k=-\infty}^{\infty}f(k).h(n - k)

La razón por la que la expresión se suma un número infinito de veces es simplemente para garantizar que la probabilidad de que las dos funciones se superpongan sea 1. La respuesta al impulso se desplaza en el tiempo infinitamente, de modo que durante algún tiempo, las dos funciones ciertamente se superpondrán. Puede parecer que sería descuidado por parte del programador ejecutar un ciclo infinito: el código puede continuar ejecutándose mientras las dos funciones no se superpongan.

La solución está en el hecho de que se están utilizando sistemas LTI. Dado que las funciones no cambian sus valores/forma con el tiempo (invariante en el tiempo), simplemente se pueden deslizar más cerca una de la otra. Recuerde que solo se requiere la salida, y no es importante «cuándo» se recibe la salida. Todos los cálculos manuales también dependen de la misma idea.

Explicación: aquí hay una técnica que se puede usar al calcular la salida:

  • Tome la señal de entrada y la respuesta al impulso como dos arrays separadas de una sola fila.
  • El primer elemento de la respuesta al impulso se multiplica con cada elemento de la señal de entrada. Este resultado se almacena.
  • El segundo elemento de la respuesta al impulso se multiplica con cada elemento de la señal de entrada. El resultado se desplaza un paso a la derecha y se almacena.
  • Los dos pasos anteriores se realizan para los elementos restantes en la respuesta de impulso.
  • Una vez que se hayan multiplicado todos los elementos, alinee todos los resultados uno debajo del otro. Refiérase a la figura de abajo.
  • Verticalmente, agregue todos los elementos en cada columna.
  • La array de una sola fila resultante es la salida convolucionada.

Explanation of Linear Convolution

Acercarse:

  • Obtenga la señal de entrada y la respuesta de impulso como dos arrays distintas .
  • Obtener una secuencia de índice de tiempo. La secuencia de índice de tiempo es una forma en que MATLAB se informa sobre cuándo comienzan nuestras funciones. Comienza en 0 por defecto, es decir, [0 1 2 3 ……..]. Sin embargo, no es necesario que la segunda secuencia o la respuesta al impulso comiencen al mismo tiempo. Se puede optar por retrasarlo o iniciarlo antes. Si se introduce un segundo antes, entonces su secuencia de índice de tiempo debe ingresarse como [-1 0 1 2 …….].
  • Utilice funciones definidas por el usuario. La función findconv() define cómo se calcula la longitud de la salida. Defina ‘ ny ‘ como la longitud de nuestro eje x en la salida. Anteriormente se definió como una array que comienza desde ‘ nybegin ‘ y se extiende hasta ‘ nyend ‘. Se hace referencia a la función calconv() en findconv() y calcula la salida real de forma secuencial tomando diferentes valores de k y n, usando 2 bucles for distintos .
  • Para cada valor de n, la suma de las salidas se calcula tomando un valor X(k) diferente en cada iteración.
  • Este resultado se almacena en una array – y(n).
  • Trazar el resultado. La función stem() se usa durante el trazado debido al hecho de que la entrada es DISCRETA por naturaleza. Si se trazara una salida de tiempo continuo, no tendría ningún sentido usar stem() ya que parecería que la salida está muestreada. Se recomienda usar plot(x_axis, y_axis) al trazar valores continuos.
  • Nota: NO varíe las longitudes de la secuencia de índice de tiempo y las secuencias 1 y 2. stem() devuelve un error que indica que no puede establecer la longitud del eje x en la salida.

A continuación se muestra el programa Matlab para implementar el enfoque anterior:

Matlab

% Matlab program to implement
% the above approach
clc;
x = input('Enter the 1st sequence: ');
nx = input('Enter the Time Index sequence: ');
h = input('Enter the second sequence: ');
nh = input('Enter the Time Index sequence: ');
  
% Sending parameters to a separate function
[y, ny] = findconv(x, nx, h, nh);
  
figure;
stem(ny, y);
xlabel('Time');
ylabel('Amplitude');
title('Linear Convolution');
disp(y);
disp(ny);
  
% Function to find the length of our output
function [y, ny] = findconv(x, nx, h, nh)
    nybegin = nx(1) + nh(1);
    nyend = nx(length(nx)) + nh(length(nh));
    ny = nybegin : nyend;
      
    % Calling a function within a function
    y = calconv(x, h);
end
  
% Here is where the summation is calculated
function [y] = calconv(x, h)
    l1 = length(x);
    l2 = length(h);
    N = l1 + l2 - 1;
    for n = 1 : 1 : N
        y(n) = 0;
        for k = 1 : 1 : l1
            if(n - k + 1 >= 1 & n - k + 1 <= l2)
                y(n) = y(n) + x(k) * h(n - k + 1);
            end
        end
    end
end

Entrada (cualquier conjunto arbitrario de números):

>> Enter the 1st Sequence: [1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17]
>> Enter the Time Index sequence: [0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16]
>> Enter the second sequence: [1 2 2 1 4 5 2 2 1 1 4 5 2 2 1 2 2]
>> Enter the Time Index sequence: [0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16]

Producción:

>> Columns 1 through 17
    1     4     9    15    25    40    57    76    96   117   142   172   204   238   273   310   349

>> Columns 18 through 33

   370   372   372   388   349   288   276   262   264   265   211   135   108    79    66    34
1st and 2nd sequence

Estas son las secuencias de entrada. Tenga en cuenta que son secuencias de tiempo discreto.

Linear convolution

La salida. Esto también es Discreto en el tiempo.

Nota: Se anima a los lectores a intentar lo mismo utilizando señales de tiempo continuo. En esos casos, la entrada se toma como una señal continua predefinida, como y = sen x. Además, use plot(x_axis, y_axis) y no stem(x_axis, y_axis).

A continuación se muestra el programa C para implementar el enfoque anterior:

C

// C program for the above approach
#include <math.h>
#include <stdio.h>
  
void calc_conv(int*, int*);
  
// Chose any length. They must
// all be equal though.
int x[10], h[10], y[10];
  
int l1, l2 = 0;
  
// Driver code
void main()
{
    printf("Enter the length of "
           "the first sequence: ");
    scanf("%d", &l1);
    printf("Enter the length of the"
           " second sequence: ");
    scanf("%d", &l2);
  
    // Delegating calculation to a
    // separate function.
    calc_conv(l1, l2);
}
  
void calc_conv(int* len1, int* len2)
{
    int l = (*len1) + (*len2) - 1;
    int i, j, n, k = 0;
  
    // Getting values of 1st sequence
    for (i = 0; i < *len1; i++) {
        scanf("%d", &x[i]);
    }
  
    // Getting values of 2nd sequence
    for (j = 0; j < *len2; j++) {
        scanf("%d", &h[i]);
    }
  
    for (n = 0; n < l; n++) {
        y[n] = 0;
        for (k = 0; k < len1; k++) {
  
            // To right shift the impulse
            if ((n - k) >= 0
                && (n - k) < *len2) {
  
                // Main calculation
                y[n] = y[n] + x[k] * h[n - k];
            }
            printf("%d\t", y[n]);
        }
    }
}

Aporte:

Enter the length of the first sequence: 4
Enter the length of the second sequence: 4
Enter x[0]: 1
Enter x[1]: 2
Enter x[2]: 3
Enter x[3]: 4
Enter h[0]: 1
Enter h[1]: 2
Enter h[2]: 2
Enter h[3]: 1

Producción:

1    4    9    15    16    11    4

Output

Publicación traducida automáticamente

Artículo escrito por siddhant_baroth y traducido por Barcelona Geeks. The original can be accessed here. Licence: CCBY-SA

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *