Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
50 changes: 50 additions & 0 deletions Convolution/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
# Convolution

## Understanding Convolution

### What Is Convolution?
Convolution is simple, but how it works looks a little tricky but not something you would never understand.
An application with which most of us are familiar will make it easy,Imagine you have a recording of someone
speaking,but there’s background noise — maybe static or hum from a fan.
If you plot the audio signal, it’s just a long 1D waveform (amplitude vs. time). The unwanted noise appears
as rapid, random fluctuations on top of the smooth speech waveform.

To reduce this noise, we can apply a low-pass filter — a small sequence of numbers (a kernel) that emphasizes
slow changes (speech patterns) and suppresses fast, noisy changes.

Here’s what happens during convolution:

You slide this filter across the audio signal.

At each step, you multiply the overlapping values and sum them up.

The resulting output is a smoothed version of the signal, where random high-frequency noise has been reduced.

Mathematically, the convolution operation combines nearby samples in a way that averages out the unwanted
fluctuations while keeping the overall structure intact.
That’s why convolution is widely used in digital signal processing — to filter out noise, enhance features, or
detect specific patterns (like beats or speech cues).
This is an example for the one dimenstional convolution we will try to implement the basic implementation which looks
mathematically daunting but it's cakewalk if you understand the implementation

### Project setup
The C code I provided will walk you through the implementation
feel free to clone this repository and try to code this up by yourself
```
git clone https://github.com/depuc/Convolution.git
```
set up your Python environment (if required):
```
python3 -m venv venv
source venv/bin/activate
```
Then install the required packages
```
pip install -r requirements.txt
```
once everything is setup you can directly run the compiled binary
```
conv
```
Tweak the code, try out floating numbers get creative.

Binary file added Convolution/conv
Binary file not shown.
2 changes: 2 additions & 0 deletions Convolution/requirements.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
numpy
matplotlib
154 changes: 154 additions & 0 deletions Convolution/src/convolve.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,154 @@
#include<stdio.h>
#include<stdlib.h>

void input_array(int *arr, int size){

for(int i = 0; i < size; i++){

scanf("%d", &arr[i]);

}

return;

}

void print_array(int *arr, int size,const char* str) {

printf("%s : ", str);

for(int i = 0; i < size; i++){

printf("%d ", arr[i]);
}

printf("\n");

return;

}

void convolve(int *filter, int *input, int *output, int M, int N){

for(int n = 0; n < M+N-1; n++){
for(int k = 0; k < M;k++){
if( (n-k >= 0) && (n-k) < N){

output[n] += filter[k]*input[n-k];
}
}
}

return;

}

void file_writer(FILE *file_pointer, int *array, int size){

for(int i = 0; i < size; i++){
fprintf(file_pointer,"%d ",array[i]);
}

fprintf(file_pointer,"\n");

return;

}

void write_to_file(const char* filename, int *filter, int* input, int* output,int M,int N,int Y){

FILE *file_pointer = fopen(filename, "w");

if(file_pointer == NULL){

printf("Error: could not open the file %s for writing",filename);
return;

}

file_writer(file_pointer,input,N);
file_writer(file_pointer,filter,M);
file_writer(file_pointer,output,Y);

fclose(file_pointer);

}

void draw_line(void){

printf("=============================\n");

}

int main(){

int M,N;

printf("ENTER INPUT SIZE-> ");
scanf("%d", &N);

printf("ENTER FILTER SIZE-> ");
scanf("%d", &M);

draw_line();

int Y = M+N-1;

int *filter = (int *)malloc(M*sizeof(int));
int *input = (int *)malloc(N*sizeof(int));
int *output = (int *)calloc(Y, sizeof(int));

if (filter == NULL || input == NULL || output == NULL) {
printf("Memory allocation failed!\n");
return 1;
}

printf("ENTER INPUT-> ");
input_array(input, N);

printf("ENTER FILTER-> ");
input_array(filter,M);

convolve(filter,input,output,M,N);

draw_line();

print_array(input,N, "INPUT ARRAY->");
print_array(filter,M, "FILTER ARRAY->");

draw_line();

print_array(output,M+N-1, "CONVOLVED ARRAY->");

draw_line();

char decision;
printf("Plot your output? [y/n]: ");

scanf(" %c",&decision);

if(decision == 'y' || decision == 'Y'){

write_to_file("data.txt",filter,input,output,M,N,Y);
free(filter);
free(input);
free(output);
system("python3 ./src/plotter.py");
return 0;

}

else{

free(filter);
free(input);
free(output);
return 0;

}

return 0;

}


53 changes: 53 additions & 0 deletions Convolution/src/plotter.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
import numpy as np
import matplotlib.pyplot as plt
import sys
import os
from matplotlib.ticker import MaxNLocator

FILENAME = "data.txt"

def plot_convolution_data():
"""Reads the data file and plots the convolution results."""
plt.style.use('dark_background')
plt.rcParams["font.family"] = "sans-serif"

try:
with open(FILENAME, 'r') as f:
lines = f.readlines()
if len(lines) < 3:
print(f"Python Error: '{FILENAME}' does not contain three lines.")
sys.exit(1)

input_signal = np.array([int(x) for x in lines[0].strip().split()])
filter_kernel = np.array([int(x) for x in lines[1].strip().split()])
output_signal = np.array([int(x) for x in lines[2].strip().split()])

except FileNotFoundError:
print(f"Python Error: Could not find '{FILENAME}'.")
sys.exit(1)
except Exception as e:
print(f"Python Error: An error occurred while reading the file: {e}")
sys.exit(1)

fig, axs = plt.subplots(3, 1, figsize=(10, 8), tight_layout=True)
fig.suptitle('Convolution Results', fontsize=18)

# Plot Input Signal
axs[0].stem(input_signal)
axs[0].set_title(f'Input Signal (Size: {len(input_signal)})')
axs[0].xaxis.set_major_locator(MaxNLocator(integer=True))

# Plot Filter Kernel
axs[1].stem(filter_kernel)
axs[1].set_title(f'Filter Kernel (Size: {len(filter_kernel)})')
axs[1].xaxis.set_major_locator(MaxNLocator(integer=True))

# Plot Output (Convolved) Signal
axs[2].stem(output_signal)
axs[2].set_title(f'Output Signal (Size: {len(output_signal)})')
axs[2].xaxis.set_major_locator(MaxNLocator(integer=True))
os.remove('data.txt')
plt.show()

if __name__ == "__main__":
plot_convolution_data()