Compare commits

...

No commits in common. "master" and "wiki" have entirely different histories.
master ... wiki

79 changed files with 3388 additions and 49470 deletions

2
.gitignore vendored
View File

@ -1,2 +0,0 @@
build/
.DS_Store

328
1DAppx.md Normal file
View File

@ -0,0 +1,328 @@
# 1D Linear vs Nonlinear Approximation using dwt #
One of the important property of wavelets is that it gives better approximation results when N largest coefficients are considered instead of first N coefficients.
[A sample code](http://code.google.com/p/wavelet1d/source/browse/trunk/demo/wavedemo2.cpp) to compare the performance of linear vs. Non-linear approximations using dwt function is given below. The signal used is "Piecewise-Regular" function from Stanford University's Matlab Wavelab Toolbox.
```
#include <iostream>
#include <fstream>
#include "wavelet.h"
#include <vector>
#include <string>
#include <cmath>
#include <algorithm>
using namespace std;
void findthresh(vector<double> vector1, int N, double& t){
sort(vector1.begin(), vector1.end(), greater<double>());
t = vector1.at(N-1);
}
int main() {
cout << "********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********" << endl; // prints
cout << "This program accepts signal from the user in a file format " << endl;
cout << "and performs Discrete Wavelet Transform with specified " << endl;
cout << "wavelet. " << endl;
cout << " " << endl;
cout << " The Following Wavelets are in the Database: " << endl;
cout << " haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10, " << endl;
cout << " db11, db12, db13, db14, db15. " << endl;
cout << " bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8, " << endl;
cout << " bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4," << endl;
cout << " bior5.5, bior6.8." << endl;
cout << " coif1, coif2, coif3, coif4, coif5." << endl;
cout << "Please Enter the Wavelet Name at the Prompt( No quotes) :" << endl;
string nm; // nm will store the name of Wavelet Family
cin >> nm;
cout << "Enter the name of signal file at the Prompt eg., signal.txt :" << endl;
char inp[50];
cin >> inp;
vector<double> sig;
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
exit(1);
}
while (sig_inp) {
double temp;
sig_inp >> temp;
sig.push_back(temp);
}
sig.pop_back();
vector<double> original;
original = sig;
cout << "Please Enter the Number of DWT Stages J :" << endl;
int J;
cin >> J ;
vector<double> dwt_output, flag;
// perform J-Level DWT
dwt(sig, J, nm, dwt_output,flag );
// Performing Linear Approximation by using only first 100 coefficients
// Coefficients in dwt_output are stored as following
// dwt_output =[ Appx(J-1) Detail(J-1) Detail(J-2) .... Detail(0)]
int n_coef = 100; // Number of significant coefficients
int n_non_sig= dwt_output.size() - n_coef; // Number of Coefficients that will
// be set to zero
dwt_output.erase(dwt_output.end()- n_non_sig,dwt_output.end());
// Deleting last n_non_sig coefficients and replacing them with zeros
dwt_output.insert(dwt_output.end(),n_non_sig,0);
ofstream linearsig("linsig.txt");
for (unsigned int i = 0; i < dwt_output.size(); i++) {
linearsig << dwt_output[i] << endl;
}
// Finding IDWT with approximated coefficients
vector<double> output;
idwt(dwt_output, flag,nm,output);
unsigned int count = output.size();
ofstream gnulinappx("gnulinappx.dat");
for (unsigned int i = 0;i < count; i++) {
gnulinappx << i << " " << output[i] << endl;
}
gnulinappx.close();
// Performing Non Linear Approximation by using only most
// significant coefficients
vector<double> dwt_output2, flag2;
// perform J-Level DWT
dwt(sig, J, nm, dwt_output2,flag2 );
double thresh = 0.0;
vector<double> temp_dwtoutput;
for (unsigned int i =0; i < dwt_output2.size();i++){
double temp = abs(dwt_output2[i]);
temp_dwtoutput.push_back(temp);
}
/*
for (unsigned int i =0; i < temp_dwtoutput.size(); i++){
cout << temp_dwtoutput[i] << endl;
}
*/
findthresh(temp_dwtoutput,n_coef, thresh);
for (unsigned int i = 0; i < dwt_output2.size();i++){
double temp = abs(dwt_output2[i]);
if (temp < thresh){
dwt_output2.at(i) = 0.0;
}
}
/*
for (unsigned int i =0; i < dwt_output2.size(); i++){
cout << dwt_output2[i] << endl;
}
*/
// Finding IDWT with approximated coefficients
vector<double> output2;
idwt(dwt_output2, flag2,nm,output2);
unsigned int count2 = output2.size();
cout << count2 << endl;
ofstream gnunlappx("gnunlappx.dat");
for (unsigned int i = 0;i < count2; i++) {
gnunlappx << i << " " << output2[i] << endl;
}
gnunlappx.close();
return 0;
}
```
This program computes DWT of the 256-point signal and then uses only 100 coefficients to reconstruct the signal. In the first case, first 100 coefficients are are used to compute linear approximation. In the second case, 100 largest coefficents are used by calculating a threshold that separates largest 100 coefficients from the other 156.The wavelet used is db3 and the signal is decomposed and reconstructd over 4 stages of DWT/IDWT. The results are plotted below.
Input Signal
![https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbqqNlUktbI/AAAAAAAAAC8/YcwG3JqEw-s/wavedemo1-1.png](https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbqqNlUktbI/AAAAAAAAAC8/YcwG3JqEw-s/wavedemo1-1.png)
Reconstructed Signal using only first 100 coefficients.(Linear Approximation)
![https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbssWS6M0AI/AAAAAAAAAEg/itai-HfR4Pc/linappx.gif](https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbssWS6M0AI/AAAAAAAAAEg/itai-HfR4Pc/linappx.gif)
Reconstructed Signal using largest 100 coefficients.(Non-Linear Approximation)
![https://lh4.googleusercontent.com/_TwtGvT0Ma-0/TbssbItgEoI/AAAAAAAAAEk/GkOTJ5cyWUA/nlappx.gif](https://lh4.googleusercontent.com/_TwtGvT0Ma-0/TbssbItgEoI/AAAAAAAAAEk/GkOTJ5cyWUA/nlappx.gif)
# 1D Linear vs Nonlinear Approximation using dwt\_sym #
_Note- Symmetric Extension DWT Implementation dwt\_sym is not a N input N output system so it has more DWT coefficients which usually means you'll need more coefficients to match dwt approximation performance for same wavelet. the trade-off is better performance at signal boundaries. In this example same number of approximation coefficients (100) are considered._
We use the same signal and wavelet family as above.[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/demo/wavedemo_sym2.cpp) is available at the source page.
```
#include <iostream>
#include <fstream>
#include "wavelet.h"
#include <vector>
#include <string>
#include <cmath>
#include <algorithm>
using namespace std;
void findthresh(vector<double> vector1, int N, double& t){
sort(vector1.begin(), vector1.end(), greater<double>());
t = vector1.at(N-1);
}
int main() {
cout << "********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********" << endl; // prints
cout << "This program accepts signal from the user in a file format " << endl;
cout << "and performs Discrete Wavelet Transform with specified " << endl;
cout << "wavelet. " << endl;
cout << " " << endl;
cout << " The Following Wavelets are in the Database: " << endl;
cout << " haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10, " << endl;
cout << " db11, db12, db13, db14, db15. " << endl;
cout << " bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8, " << endl;
cout << " bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4," << endl;
cout << " bior5.5, bior6.8." << endl;
cout << " coif1, coif2, coif3, coif4, coif5." << endl;
cout << "Please Enter the Wavelet Name at the Prompt( No quotes) :" << endl;
string nm; // nm will store the name of Wavelet Family
cin >> nm;
cout << "Enter the name of signal file at the Prompt eg., signal.txt :" << endl;
char inp[50];
cin >> inp;
vector<double> sig;
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
exit(1);
}
while (sig_inp) {
double temp;
sig_inp >> temp;
sig.push_back(temp);
}
sig.pop_back();
vector<double> original;
original = sig;
cout << "Please Enter the Number of DWT Stages J :" << endl;
int J;
cin >> J ;
vector<double> dwt_output, flag;
vector<int> length1;
int ext = 2;
// perform J-Level DWT
dwt_sym(sig, J, nm, dwt_output,flag, length1,ext );
// Performing Linear Approximation by using only first 100 coefficients
// Coefficients in dwt_output are stored as following
// dwt_output =[ Appx(J-1) Detail(J-1) Detail(J-2) .... Detail(0)]
int n_coef = 100; // Number of significant coefficients
int n_non_sig= dwt_output.size() - n_coef; // Number of Coefficients that will
// be set to zero
dwt_output.erase(dwt_output.end()- n_non_sig,dwt_output.end());
// Deleting last n_non_sig coefficients and replacing them with zeros
dwt_output.insert(dwt_output.end(),n_non_sig,0);
ofstream linearsig("linsig.txt");
for (unsigned int i = 0; i < dwt_output.size(); i++) {
linearsig << dwt_output[i] << endl;
}
// Finding IDWT with approximated coefficients
vector<double> output;
idwt_sym(dwt_output, flag,nm,output, length1);
unsigned int count = output.size();
ofstream gnulinappx("gnulinappx.dat");
for (unsigned int i = 0;i < count; i++) {
gnulinappx << i << " " << output[i] << endl;
}
gnulinappx.close();
// Performing Non Linear Approximation by using only most
// significant coefficients
vector<double> dwt_output2, flag2;
vector<int> length2;
// perform J-Level DWT
dwt_sym(sig, J, nm, dwt_output2,flag2,length2, ext );
double thresh = 0.0;
vector<double> temp_dwtoutput;
for (unsigned int i =0; i < dwt_output2.size();i++){
double temp = abs(dwt_output2[i]);
temp_dwtoutput.push_back(temp);
}
/*
for (unsigned int i =0; i < temp_dwtoutput.size(); i++){
cout << temp_dwtoutput[i] << endl;
}
*/
findthresh(temp_dwtoutput,n_coef, thresh);
for (unsigned int i = 0; i < dwt_output2.size();i++){
double temp = abs(dwt_output2[i]);
if (temp < thresh){
dwt_output2.at(i) = 0.0;
}
}
/*
for (unsigned int i =0; i < dwt_output2.size(); i++){
cout << dwt_output2[i] << endl;
}
*/
// Finding IDWT with approximated coefficients
vector<double> output2;
idwt_sym(dwt_output2, flag2,nm,output2, length2);
unsigned int count2 = output2.size();
cout << count2 << endl;
ofstream gnunlappx("gnunlappx.dat");
for (unsigned int i = 0;i < count2; i++) {
gnunlappx << i << " " << output2[i] << endl;
}
gnunlappx.close();
return 0;
}
```
Reconstructed Signal using only first 100 coefficients.(Linear Approximation)
![https://lh6.googleusercontent.com/_TwtGvT0Ma-0/Tbsre73jQxI/AAAAAAAAAEY/ffRAs9icfhM/symlinappx.gif](https://lh6.googleusercontent.com/_TwtGvT0Ma-0/Tbsre73jQxI/AAAAAAAAAEY/ffRAs9icfhM/symlinappx.gif)
Reconstructed Signal using largest 100 coefficients.(Non-Linear Approximation)
![https://lh4.googleusercontent.com/_TwtGvT0Ma-0/TbsrfWkT2sI/AAAAAAAAAEc/4vf49wiYHtM/symnlappx.gif](https://lh4.googleusercontent.com/_TwtGvT0Ma-0/TbsrfWkT2sI/AAAAAAAAAEc/4vf49wiYHtM/symnlappx.gif)

126
1DDWTdemo.md Normal file
View File

@ -0,0 +1,126 @@
# 1D DWT/IDWT Demo using dwt function #
[A sample code](http://code.google.com/p/wavelet1d/source/browse/trunk/demo/wavedemo1.cpp) for DWT/IDWT for a given signal is given below. The signal used is "Piecewise-Regular" function from Stanford University's Matlab Wavelab Toolbox.
```
#include <iostream>
#include <fstream>
#include "wavelet.h"
#include <vector>
#include <string>
#include <cmath>
using namespace std;
int main() {
cout << "********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********" << endl; // prints
cout << "This program accepts signal from the user in a file format " << endl;
cout << "and performs Discrete Wavelet Transform with specified " << endl;
cout << "wavelet. " << endl;
cout << " " << endl;
cout << " The Following Wavelets are in the Database: " << endl;
cout << " haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10, " << endl;
cout << " db11, db12, db13, db14, db15. " << endl;
cout << " bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8, " << endl;
cout << " bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4," << endl;
cout << " bior5.5, bior6.8." << endl;
cout << " coif1, coif2, coif3, coif4, coif5." << endl;
cout << "Please Enter the Wavelet Name at the Prompt( No quotes) :" << endl;
string nm; // nm will store the name of Wavelet Family
cin >> nm;
cout << "Enter the name of signal file at the Prompt eg., signal.txt :" << endl;
char inp[50];
cin >> inp;
vector<double> sig;
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
exit(1);
}
while (sig_inp) {
double temp;
sig_inp >> temp;
sig.push_back(temp);
}
sig.pop_back();
vector<double> original;
original = sig;
cout << "Please Enter the Number of DWT Stages J :" << endl;
int J;
cin >> J ;
vector<double> dwt_output, flag;
// perform J-Level DWT
dwt(sig, J, nm, dwt_output,flag );
//Perform J-Level IDWT
vector<double> output;
idwt(dwt_output, flag,nm,output);
ofstream sig1("recon.txt");
ofstream diff("diff.txt");
cout <<" Recon signal size" << output.size() << endl;
for (unsigned int i = 0; i < output.size(); i++){
sig1 << output[i] << endl;
diff << output[i] - original[i] << endl;
}
gnudwtplot(J);
return 0;
}
```
The program asks user for wavelet name, signal file and number of DWT stages. It then computes DWT of the input signal and then the IDWT from the wavelet coefficients so obtained. Running the program from Eclipse console :
```
********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********
This program accepts signal from the user in a file format
and performs Discrete Wavelet Transform with specified
wavelet.
The Following Wavelets are in the Database:
haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10,
db11, db12, db13, db14, db15.
bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8,
bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4,
bior5.5, bior6.8.
coif1, coif2, coif3, coif4, coif5.
Please Enter the Wavelet Name at the Prompt( No quotes) :
db3
Enter the name of signal file at the Prompt eg., signal.txt :
signal.txt
Please Enter the Number of DWT Stages J :
3
```
gnudwtplot(J) is called which generates GNUPLOT script. GNUPLOT script is called from gnuplot as following.
gnuplot> cd '<Path to File Outputs>'
gnuplot> load "gnudwt.gnu.txt"
1. Input Signal : Piecewise-Regular signal from Stanford University Wavelab Toolbox.
![https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbqqNlUktbI/AAAAAAAAAC8/YcwG3JqEw-s/wavedemo1-1.png](https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbqqNlUktbI/AAAAAAAAAC8/YcwG3JqEw-s/wavedemo1-1.png)
2. Approximation and Detail coefficients at each iteration stage. Note- While the program is plotting approximation coefficients, the actual DWT doesn't store approximation values at each level for redundancy reasons. Only approximation coefficients at the Jth stage are stored.
![https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TbqqNoZC6fI/AAAAAAAAAC0/zWiH8iSn-2k/s912/wavedemo1-2.png](https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TbqqNoZC6fI/AAAAAAAAAC0/zWiH8iSn-2k/s912/wavedemo1-2.png)
3. Four filters associated with orthogonal db3 wavelet.
![https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TbqqOIJg76I/AAAAAAAAADA/EfV7aPfz6GY/wavedemo1-3.png](https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TbqqOIJg76I/AAAAAAAAADA/EfV7aPfz6GY/wavedemo1-3.png)
4. Reconstructed Signal.
![https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbqqOaERebI/AAAAAAAAADI/EfxtbRPdYq4/wavedemo1-4.png](https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbqqOaERebI/AAAAAAAAADI/EfxtbRPdYq4/wavedemo1-4.png)
# 1D DWT/IDWT Demo using dwt\_sym function #
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/demo/wavedemo_sym1.cpp) for DWT/IDWT using dwt\_sym function is also available.

91
1DSWTDemo.md Normal file
View File

@ -0,0 +1,91 @@
# 1D Stationary Wavelet Transform Demo #
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/demo/swtdemo.cpp)
```
//============================================================================
// Name : swtdemo.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : 1D Stationary Wavelet Transform Demo
//============================================================================
#include <iostream>
#include <fstream>
#include "wavelet.h"
#include <vector>
#include <string>
#include <cmath>
using namespace std;
int main() {
cout << "********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********" << endl; // prints
cout << "This program accepts signal from the user in a file format " << endl;
cout << "and performs Discrete Wavelet Transform with specified " << endl;
cout << "wavelet. " << endl;
cout << " " << endl;
cout << " The Following Wavelets are in the Database: " << endl;
cout << " haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10, " << endl;
cout << " db11, db12, db13, db14, db15. " << endl;
cout << " bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8, " << endl;
cout << " bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4," << endl;
cout << " bior5.5, bior6.8." << endl;
cout << " coif1, coif2, coif3, coif4, coif5." << endl;
cout << "Please Enter the Wavelet Name at the Prompt( No quotes) :" << endl;
string nm; // nm will store the name of Wavelet Family
cin >> nm;
cout << "Enter the name of signal file at the Prompt eg., signal.txt :" << endl;
char inp[50];
cin >> inp;
vector<double> sig;
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
exit(1);
}
while (sig_inp) {
double temp;
sig_inp >> temp;
sig.push_back(temp);
}
sig.pop_back();
vector<double> original;
original = sig;
cout << "Please Enter the Number of DWT Stages J :" << endl;
int J;
cin >> J ;
vector<double> swt_output;
// perform J-Level DWT
int length;// All coefficients are of same length. Variable "length" returns length
// of coefficients. It is not required for ISWT computations.
// If signal is not of dyadic length it is zeropadded as the algorithm is designed to
// work with signals of 2^M length. These extra zeros can be removed after reconstruction.
swt(sig, J, nm, swt_output, length);
vector<double> iswt_output;
iswt(swt_output,J, nm,iswt_output);
gnuswtplot(J);
return 0;
}
```
The signal is the same Piecewise Regular signal that is used in the [1D Decimated DWT Demo](http://code.google.com/p/wavelet1d/wiki/1DDWTdemo).
![https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbqqNlUktbI/AAAAAAAAAC8/YcwG3JqEw-s/wavedemo1-1.png](https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbqqNlUktbI/AAAAAAAAAC8/YcwG3JqEw-s/wavedemo1-1.png)
> The filter used is Daubechies db2 Orthogonal length=4 filter. The undecimated detail and approximation coefficients are plotted as following using GNUPLOT.
![https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TchqBRDzvzI/AAAAAAAAAFQ/OUMcPMT554s/swtdisp.png](https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TchqBRDzvzI/AAAAAAAAAFQ/OUMcPMT554s/swtdisp.png)
> There is a very obvious trade-off here. The Transform is good for signal analysis as details and approximation coefficients are of the same length as the original signal at every decomposition stage but the system is highly redundant.
> The Inverse SWT is perfect reconstruction.

670
2DAppx.md Normal file
View File

@ -0,0 +1,670 @@
# Image Approximation using dwt\_2d #
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/demo/imagedemo2.cpp)
```
#include <iostream>
#include <fstream>
#include <string>
#include <vector>
#include <cmath>
#include <algorithm>
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
#include "wavelet.h"
using namespace std;
using namespace cv;
void findthresh(vector<double> &vector1, int N, double& t){
sort(vector1.begin(), vector1.end(), greater<double>());
t = vector1.at(N-1);
}
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
void* minval(vector<vector<double> > &arr, double &min){
min = 10000;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (min >= arr[i][j]){
min = arr[i][j];
}
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("lena512.bmp");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
int rr1,cc1;
string nm = "db3";
// Finding DWT output dimensions as the DWT output is zeropadded
dwt_output_dim(vec1, rr1, cc1 );
int J = 5;
vector<double> flag;
vector<vector<double> > dwt_output(rr1, vector<double>(cc1));
cout << rr1 << cc1 << "size of op" << endl;
// Computing 2d DWT ( vec1 is the signal while dwt_output is the DWT output)
dwt_2d(vec1, J, nm, dwt_output,flag );
cout << "dwt size" << dwt_output.size() << dwt_output[0].size() << endl;
double max,min;
maxval(dwt_output,max);
minval(dwt_output,min);
cout << "maxval" << max << " minval" << min << endl;
vector<vector<double> > dwt_coef1(rr1, vector<double>(cc1));
vector<vector<double> > dwt_coef2(rr1, vector<double>(cc1));
// Storing dwt_output for two different computations based on
// different approximation values
dwt_coef1 = dwt_output;
dwt_coef2 = dwt_output;
//Displaying Scaled Image
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = cc1;
imgSize.height = rr1;
cvImg = cvCreateImage( imgSize, 8, 1 );
// Setting coefficients of created image to the scaled DWT output values
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( dwt_output[i][j] <= 0.0){
dwt_output[i][j] = 0.0;
}
if ( i <= (imgSize.height/pow(2.0,double(J))) && j <= (imgSize.width/pow(2.0,double(J))) ) {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (dwt_output[i][j] / max) * 255.0);
} else {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) (dwt_output[i][j]) ;
}
}
}
// IMPORTANT -- dwt_output value has been modified above.
cvNamedWindow( "DWT Image", 1 ); // creation of a visualisation window
cvShowImage( "DWT Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("DWT Image");
// Case 1 : Only 10% of the largest coefficients are considered
// Total elements in the original image is rows * cols
int n_coef1= int (( rows * cols)/ 10);
// Finding Threshold Value corresponding to n_coef1
vector<double> temp1;
cout << "size: " << (int) temp1.size() << "\n";
cout << "capacity: " << (int) temp1.capacity() << "\n";
cout << "max_size: " << (int) temp1.max_size() << "\n";
for (int i =0; i < rr1; i++) {
for (int j = 0; j < cc1; j++){
double tempval = abs(dwt_coef1[i][j]);
temp1.push_back(tempval);
}
}
double thresh1= 0.0;
findthresh(temp1,n_coef1,thresh1);
ofstream temp("temp.txt");
for (int i =0; i < rows * cols; i++){
temp << temp1[i] << " " ;
}
// Reset coeffficients value depending on threshold value
for (int i =0; i < rr1; i++) {
for (int j = 0; j < cc1; j++){
double temp = abs(dwt_coef1[i][j]);
if (temp < thresh1){
dwt_coef1[i][j] = 0.0;
}
}
}
// Finding IDWT
vector<vector<double> > final(rr1, vector<double>(cc1));
idwt_2d(dwt_coef1,flag, nm ,final);
// Removing Zeropadding
zero_remove(vec1,final);
double max1;
maxval(final,max1);
//Displaying Reconstructed Image
IplImage *dvImg;
CvSize dvSize; // size of output image
dvSize.width = final[0].size();
dvSize.height = final.size();
dvImg = cvCreateImage( dvSize, 8, 1 );
for (int i = 0; i < dvSize.height; i++ ) {
for (int j = 0; j < dvSize.width; j++ ){
if ( final[i][j] <= 0.0){
final[i][j] = 0.0;
}
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) ((final[i][j]/max1) * 255) ;
}
}
cvNamedWindow( "10% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "10% Coeff Reconstructed Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("10% Coeff Reconstructed Image");
// Case 2 : Only 2% of the largest coefficients are considered
// Total elements in the original image is rows * cols
int n_coef2= int (( rows * cols) / 50);
// Finding Threshold Value corresponding to n_coef1
vector<double> temp2;
for (int i =0; i < rr1; i++) {
for (int j = 0; j < cc1; j++){
double tempval = abs(dwt_coef2[i][j]);
temp2.push_back(tempval);
}
}
double thresh2= 0.0;
findthresh(temp2,n_coef2,thresh2);
// Reset coeffficients value depending on threshold value
for (int i =0; i < rr1; i++) {
for (int j = 0; j < cc1; j++){
double temp = abs(dwt_coef2[i][j]);
if (temp < thresh2){
dwt_coef2[i][j] = 0.0;
}
}
}
// Finding IDWT
vector<vector<double> > final2(rr1, vector<double>(cc1));
idwt_2d(dwt_coef2,flag, nm ,final2);
// Removing Zeropadding
zero_remove(vec1,final2);
double max2;
maxval(final2,max2);
//Displaying Reconstructed Image
IplImage *dvImg2;
CvSize dvSize2; // size of output image
dvSize2.width = final2[0].size();
dvSize2.height = final2.size();
dvImg2 = cvCreateImage( dvSize2, 8, 1 );
for (int i = 0; i < dvSize2.height; i++ ) {
for (int j = 0; j < dvSize2.width; j++ ){
if ( final2[i][j] <= 0.0){
final2[i][j] = 0.0;
}
((uchar*)(dvImg2->imageData + dvImg2->widthStep*i))[j] =
(char) ((final2[i][j]/ max2)* 255) ;
}
}
cvNamedWindow( "2% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "2% Coeff Reconstructed Image", dvImg2 ); // image visualisation
cvWaitKey();
cvDestroyWindow("2% Coeff Reconstructed Image");
cout << thresh1 << " " << thresh2 << endl;
return 0;
}
```
This code decomposes a 512X512 grayscale image to 6 levels and uses a) only 10% coefficients and b) only 2% coefficients to reconstruct the image.
Input Image
![https://lh5.googleusercontent.com/_TwtGvT0Ma-0/Tbs9nUUIJeI/AAAAAAAAAEs/PeIvmkAA-4w/orig.jpg](https://lh5.googleusercontent.com/_TwtGvT0Ma-0/Tbs9nUUIJeI/AAAAAAAAAEs/PeIvmkAA-4w/orig.jpg)
DWT of Input Image
![https://lh3.googleusercontent.com/_TwtGvT0Ma-0/Tbs9tjSVydI/AAAAAAAAAEw/GOdQ8m_HrEM/dwt.jpg](https://lh3.googleusercontent.com/_TwtGvT0Ma-0/Tbs9tjSVydI/AAAAAAAAAEw/GOdQ8m_HrEM/dwt.jpg)
Image Approximation using only 10% coefficients
![https://lh3.googleusercontent.com/_TwtGvT0Ma-0/Tbs9xeEOw0I/AAAAAAAAAE0/aHtjobIlBrI/recon.jpg](https://lh3.googleusercontent.com/_TwtGvT0Ma-0/Tbs9xeEOw0I/AAAAAAAAAE0/aHtjobIlBrI/recon.jpg)
Image Aprroximation using only 2% coefficients.
![https://lh4.googleusercontent.com/_TwtGvT0Ma-0/Tbs93AM0gLI/AAAAAAAAAE4/y0SbOGpRmKI/recon2.jpg](https://lh4.googleusercontent.com/_TwtGvT0Ma-0/Tbs93AM0gLI/AAAAAAAAAE4/y0SbOGpRmKI/recon2.jpg)
# Image Approximation using dwt\_2d\_sym #
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/demo/imagedemo_sym2.cpp)
```
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <complex>
#include <cmath>
#include <algorithm>
#include "wavelet.h"
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
using namespace std;
using namespace cv;
void findthresh(vector<double> &vector1, int N, double& t){
sort(vector1.begin(), vector1.end(), greater<double>());
t = vector1.at(N-1);
}
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
void* maxval1(vector<double> &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
if (max <= arr[i]){
max = arr[i];
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("lena512.bmp");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
cvSaveImage("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
string nm = "db2";
vector<double> l1,h1,l2,h2;
filtcoef(nm,l1,h1,l2,h2);
// unsigned int lf=l1.size();
// int rows_n =(int) (rows+ J*(lf-1));
// int cols_n =(int) (cols + J * ( lf -1));
// Finding 2D DWT Transform of the image using symetric extension algorithm
// Extension is set to 0 (eg., int e = 0)
vector<int> length;
vector<double> output,flag;
int J =6;
int e=0;
dwt_2d_sym(vec1,J,nm,output,flag,length,e);
double max;
vector<int> length2;
// This algorithm computes DWT of image of any given size. Together with convolution and
// subsampling operations it is clear that subsampled images are of different length than
// dyadic length images. In order to compute the "effective" size of DWT we do additional
// calculations.
dwt_output_dim_sym(length,length2,J);
// length2 is gives the integer vector that contains the size of subimages that will
// combine to form the displayed output image. The last two entries of length2 gives the
// size of DWT ( rows_n by cols_n)
int siz = length2.size();
int rows_n=length2[siz-2];
int cols_n = length2[siz-1];
vector<vector< double> > dwtdisp(rows_n, vector<double>(cols_n));
dispDWT(output,dwtdisp, length ,length2, J);
// dispDWT returns the 2D object dwtdisp which will be displayed using OPENCV's image
// handling functions
vector<vector<double> > dwt_output= dwtdisp;
// Stroing the DWT coefficients in two different vectors that will be used to approximate
// Image with two different sets of chosen coefficients.
vector<double> dwt_coef1;
vector<double> dwt_coef2;
dwt_coef1 = output;
dwt_coef2 = output;
maxval(dwt_output,max);// max value is needed to take care of overflow which happens because
// of convolution operations performed on unsigned 8 bit images
//Displaying Scaled Image
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = cols_n;
imgSize.height = rows_n;
cvImg = cvCreateImage( imgSize, 8, 1 );
// dwt_hold is created to hold the dwt output as further operations need to be
// carried out on dwt_output in order to display scaled images.
vector<vector<double> > dwt_hold(rows_n, vector<double>( cols_n));
dwt_hold = dwt_output;
// Setting coefficients of created image to the scaled DWT output values
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( dwt_output[i][j] <= 0.0){
dwt_output[i][j] = 0.0;
}
if ( i <= (length2[0]) && j <= (length2[1]) ) {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (dwt_output[i][j] / max) * 255.0);
} else {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) (dwt_output[i][j]) ;
}
}
}
cvNamedWindow( "DWT Image", 1 ); // creation of a visualisation window
cvShowImage( "DWT Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("DWT Image");
cvSaveImage("dwt.bmp",cvImg);
// Case 1 : Only 10% of the largest coefficients are considered
// Output is the 1D DWT vector
int n_coef1= int (output.size()/ 10);
cout << n_coef1 << endl;
// Finding Threshold Value corresponding to n_coef1
vector<double> temp1;
cout << "size: " << (int) temp1.size() << "\n";
cout << "capacity: " << (int) temp1.capacity() << "\n";
cout << "max_size: " << (int) temp1.max_size() << "\n";
for (unsigned int i =0; i < dwt_coef1.size(); i++) {
double tempval = abs(dwt_coef1[i]);
temp1.push_back(tempval);
}
double thresh1= 0.0;
findthresh(temp1,n_coef1,thresh1);
cout << "thresh" << thresh1 << endl;
ofstream temp("temp.txt");
for (unsigned int i =0; i < temp1.size(); i++){
temp << temp1[i] << " " ;
}
// Reset coeffficients value depending on threshold value
for (unsigned int i =0; i < dwt_coef1.size(); i++) {
double temp = abs(dwt_coef1[i]);
if (temp < thresh1){
dwt_coef1.at(i)= 0.0;
}
}
// Finding IDWT
vector<vector<double> > idwt_output(rows, vector<double>(cols));
idwt_2d_sym( dwt_coef1,flag, nm, idwt_output,length);
double max1;
maxval(idwt_output,max1);
//Displaying Reconstructed Image
IplImage *dvImg;
CvSize dvSize; // size of output image
dvSize.width = idwt_output[0].size();
dvSize.height = idwt_output.size();
cout << idwt_output.size() << idwt_output[0].size() << endl;
dvImg = cvCreateImage( dvSize, 8, 1 );
for (int i = 0; i < dvSize.height; i++ ){
for (int j = 0; j < dvSize.width; j++ ){
if ( idwt_output[i][j] <= 0.0){
idwt_output[i][j] = 0.0;
}
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) ((idwt_output[i][j] / max1) * 255 ) ;
}
}
cvNamedWindow( "10% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "10% Coeff Reconstructed Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("10% Coeff Reconstructed Image");
cvSaveImage("recon.bmp",dvImg);
// Case 2 : Only 2% of the largest coefficients are considered
// Output is the 1D DWT vector
int n_coef2= int (output.size()/ 50);
cout << n_coef2 << endl;
// Finding Threshold Value corresponding to n_coef1
vector<double> temp2;
for (unsigned int i =0; i < dwt_coef2.size(); i++) {
double tempval = abs(dwt_coef2[i]);
temp2.push_back(tempval);
}
double thresh2= 0.0;
findthresh(temp2,n_coef2,thresh2);
cout << "thresh" << thresh2 << endl;
// Reset coeffficients value depending on threshold value
for (unsigned int i =0; i < dwt_coef2.size(); i++) {
double temp = abs(dwt_coef2[i]);
if (temp < thresh2){
dwt_coef2.at(i)= 0.0;
}
}
// Finding IDWT
vector<vector<double> > idwt_output2(rows, vector<double>(cols));
idwt_2d_sym( dwt_coef2,flag, nm, idwt_output2,length);
double max2;
maxval(idwt_output2,max2);
//Displaying Reconstructed Image
IplImage *dvImg2;
CvSize dvSize2; // size of output image
dvSize2.width = idwt_output2[0].size();
dvSize2.height = idwt_output2.size();
cout << idwt_output2.size() << idwt_output2[0].size() << endl;
dvImg2 = cvCreateImage( dvSize2, 8, 1 );
for (int i = 0; i < dvSize2.height; i++ ) {
for (int j = 0; j < dvSize2.width; j++ ) {
if ( idwt_output2[i][j] <= 0.0){
idwt_output2[i][j] = 0.0;
}
((uchar*)(dvImg2->imageData + dvImg2->widthStep*i))[j] =
(char) ((idwt_output2[i][j]/ max2) * 255 ) ;
}
}
cvNamedWindow( "2% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "2% Coeff Reconstructed Image", dvImg2 ); // image visualisation
cvWaitKey();
cvDestroyWindow("2% Coeff Reconstructed Image");
cvSaveImage("recon2.bmp",dvImg2);
return 0;
}
```
Same image is used as above. The decomposition level and wavelet family are same as well.
DWT of the Input Image
![https://lh6.googleusercontent.com/_TwtGvT0Ma-0/TbqskwpEcwI/AAAAAAAAAEE/mxHqRhlxWBw/dwt.jpg](https://lh6.googleusercontent.com/_TwtGvT0Ma-0/TbqskwpEcwI/AAAAAAAAAEE/mxHqRhlxWBw/dwt.jpg)
Image Approximation using only 10% coefficients
![https://lh6.googleusercontent.com/_TwtGvT0Ma-0/TbqsgwhYV4I/AAAAAAAAAEA/aclJXuNL1QY/recon.jpg](https://lh6.googleusercontent.com/_TwtGvT0Ma-0/TbqsgwhYV4I/AAAAAAAAAEA/aclJXuNL1QY/recon.jpg)
Image Aprroximation using only 2% coefficients.
![https://lh4.googleusercontent.com/_TwtGvT0Ma-0/TbqsVnzTMpI/AAAAAAAAAD4/Dz2LiabXVmc/recon2.jpg](https://lh4.googleusercontent.com/_TwtGvT0Ma-0/TbqsVnzTMpI/AAAAAAAAAD4/Dz2LiabXVmc/recon2.jpg)

421
2DDWTdemo.md Normal file
View File

@ -0,0 +1,421 @@
# 2D DWT Demo using dwt\_2d #
_Note- I am using OPENCV to handle image I/O and other basic functionalities so most of the code will be different if you are using different libraries or software. Even if you are using OPENCV, you may not want to use the suboptimal algorithm I have used to tackle the UINT8 image coefficient overflow issues. This isn't something I have paid much attention to and this code is just to demonstrate DWT/IDWT functionality of the library._
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/demo/imagedemo1.cpp) to compute DWT/IDWT of a 512X512 grayscale image is as following
```
#include <iostream>
#include <fstream>
#include <string>
#include <vector>
#include <cmath>
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
#include "wavelet.h"
using namespace std;
using namespace cv;
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
void* minval(vector<vector<double> > &arr, double &min){
min = 10000;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (min >= arr[i][j]){
min = arr[i][j];
}
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("lena512.bmp");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
cvSaveImage("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
int rr1,cc1;
string nm = "db4";
// Finding DWT output dimensions as the DWT output is zeropadded
dwt_output_dim(vec1, rr1, cc1 );
int J = 2;
vector<double> flag;
vector<vector<double> > dwt_output(rr1, vector<double>(cc1));
cout << rr1 << cc1 << "size of op" << endl;
// Computing 2d DWT ( vec1 is the signal while dwt_output is the DWT output)
dwt_2d(vec1, J, nm, dwt_output,flag );
cout << "dwt size" << dwt_output.size() << dwt_output[0].size() << endl;
double max,min;
maxval(dwt_output,max);
minval(dwt_output,min);
cout << "maxval" << max << " minval" << min << endl;
//Displaying Scaled Image
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = cc1;
imgSize.height = rr1;
cvImg = cvCreateImage( imgSize, 8, 1 );
// dwt_hold is created to hold the dwt output as further operations need to be
// carried out on dwt_output in order to display scaled images.
vector<vector<double> > dwt_hold(rr1, vector<double>(cc1));
dwt_hold = dwt_output;
// Setting coefficients of created image to the scaled DWT output values
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( dwt_output[i][j] <= 0.0){
dwt_output[i][j] = 0.0;
}
if ( i <= (imgSize.height/pow(2.0,double(J))) && j <= (imgSize.width/pow(2.0,double(J))) ) {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (dwt_output[i][j] / max) * 255.0);
} else {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) (dwt_output[i][j]) ;
}
}
}
cvNamedWindow( "DWT Image", 1 ); // creation of a visualisation window
cvShowImage( "DWT Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("DWT Image");
cvSaveImage("dwt.bmp",cvImg);
// Finding IDWT
vector<vector<double> > final(rr1, vector<double>(cc1));
idwt_2d(dwt_hold,flag, nm ,final);
// Removing Zeropadding
zero_remove(vec1,final);
//Displaying Reconstructed Image
IplImage *dvImg;
CvSize dvSize; // size of output image
dvSize.width = final[0].size();
dvSize.height = final.size();
dvImg = cvCreateImage( dvSize, 8, 1 );
for (int i = 0; i < dvSize.height; i++ )
for (int j = 0; j < dvSize.width; j++ )
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) (final[i][j]) ;
cvNamedWindow( "Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "Reconstructed Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("Reconstructed Image");
cvSaveImage("recon.bmp",dvImg);
ofstream diff("diff.dat");
for (unsigned int i=0; i < final.size(); i++) {
for (unsigned int j = 0; j < final[0].size(); j++) {
diff << final[i][j]-vec1[i][j] << " " ;
}
diff << endl;
}
ofstream recon("recon.dat");
for (unsigned int i=0; i < final.size(); i++) {
for (unsigned int j = 0; j < final[0].size(); j++) {
recon << (int)final[i][j] << " " ;
}
recon << endl;
}
ofstream orig("orig.dat");
for (unsigned int i=0; i < vec1.size(); i++) {
for (unsigned int j = 0; j < vec1[0].size(); j++) {
orig << (int)vec1[i][j] << " " ;
}
orig << endl;
}
return 0;
}
```
Input Image in this example is 512X512 "Lena" grayscale image.
![https://lh6.googleusercontent.com/_TwtGvT0Ma-0/TbqrRs2Ze1I/AAAAAAAAADY/7TQUtL2FFHk/orig.jpg](https://lh6.googleusercontent.com/_TwtGvT0Ma-0/TbqrRs2Ze1I/AAAAAAAAADY/7TQUtL2FFHk/orig.jpg)
Two Level DWT of this image is computed with Daubechies' db4 wavelet.
![https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TbqrZCUoi2I/AAAAAAAAADc/l_jWn24PQcs/dwt.jpg](https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TbqrZCUoi2I/AAAAAAAAADc/l_jWn24PQcs/dwt.jpg)
Reconstructed Image is computed using idwt\_2d function.
![https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbqrftMQhCI/AAAAAAAAADg/58m4OlfoxvM/recon.jpg](https://lh5.googleusercontent.com/_TwtGvT0Ma-0/TbqrftMQhCI/AAAAAAAAADg/58m4OlfoxvM/recon.jpg)
_Additional Note About dwt\_2d- This implementation is a NXN input and NXN output system designed to work with dyadic lengths N. If the image dimensions are not dyadic, dwt\_2d will zeropad to make it NXN and you will end up with lots of zeros depending on the original size. The algorithm below (dwt\_2d\_sym) is designed to handle any image size but there are redundancies in the DWT stage as it is not a NXN I/O system._
# 2D DWT Demo using dwt\_2d\_sym #
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/demo/imagedemo_sym.cpp) to compute DWT/IDWT using symmetric extension dwt\_2d\_sym is as follows
```
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <complex>
#include <cmath>
#include <algorithm>
#include "wavelet.h"
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
using namespace std;
using namespace cv;
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
void* maxval1(vector<double> &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
if (max <= arr[i]){
max = arr[i];
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("Fig10.04(a).jpg");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
cvSaveImage("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
string nm = "db3";
vector<double> l1,h1,l2,h2;
filtcoef(nm,l1,h1,l2,h2);
// unsigned int lf=l1.size();
// int rows_n =(int) (rows+ J*(lf-1));
// int cols_n =(int) (cols + J * ( lf -1));
// Finding 2D DWT Transform of the image using symetric extension algorithm
// Extension is set to 3 (eg., int e = 3)
vector<int> length;
vector<double> output,flag;
int J =3;
int e=3;
dwt_2d_sym(vec1,J,nm,output,flag,length,e);
double max;
vector<int> length2;
// This algorithm computes DWT of image of any given size. Together with convolution and
// subsampling operations it is clear that subsampled images are of different length than
// dyadic length images. In order to compute the "effective" size of DWT we do additional
// calculations.
dwt_output_dim_sym(length,length2,J);
// length2 is gives the integer vector that contains the size of subimages that will
// combine to form the displayed output image. The last two entries of length2 gives the
// size of DWT ( rows_n by cols_n)
int siz = length2.size();
int rows_n=length2[siz-2];
int cols_n = length2[siz-1];
vector<vector< double> > dwtdisp(rows_n, vector<double>(cols_n));
dispDWT(output,dwtdisp, length ,length2, J);
// dispDWT returns the 2D object dwtdisp which will be displayed using OPENCV's image
// handling functions
vector<vector<double> > dwt_output= dwtdisp;
maxval(dwt_output,max);// max value is needed to take care of overflow which happens because
// of convolution operations performed on unsigned 8 bit images
//Displaying Scaled Image
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = cols_n;
imgSize.height = rows_n;
cvImg = cvCreateImage( imgSize, 8, 1 );
// dwt_hold is created to hold the dwt output as further operations need to be
// carried out on dwt_output in order to display scaled images.
vector<vector<double> > dwt_hold(rows_n, vector<double>( cols_n));
dwt_hold = dwt_output;
// Setting coefficients of created image to the scaled DWT output values
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( dwt_output[i][j] <= 0.0){
dwt_output[i][j] = 0.0;
}
if ( i <= (length2[0]) && j <= (length2[1]) ) {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (dwt_output[i][j] / max) * 255.0);
} else {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) (dwt_output[i][j]) ;
}
}
}
cvNamedWindow( "DWT Image", 1 ); // creation of a visualisation window
cvShowImage( "DWT Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("DWT Image");
cvSaveImage("dwt.bmp",cvImg);
// Finding IDWT
vector<vector<double> > idwt_output(rows, vector<double>(cols));
idwt_2d_sym( output,flag, nm, idwt_output,length);
//Displaying Reconstructed Image
IplImage *dvImg;
CvSize dvSize; // size of output image
dvSize.width = idwt_output[0].size();
dvSize.height = idwt_output.size();
cout << idwt_output.size() << idwt_output[0].size() << endl;
dvImg = cvCreateImage( dvSize, 8, 1 );
for (int i = 0; i < dvSize.height; i++ )
for (int j = 0; j < dvSize.width; j++ )
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) (idwt_output[i][j]) ;
cvNamedWindow( "Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "Reconstructed Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("Reconstructed Image");
cvSaveImage("recon.bmp",dvImg);
return 0;
}
```
Input Image is a 486X486 grayscale image taken from [Image Processing Place Database](http://www.imageprocessingplace.com/root_files_V3/image_databases.htm).
![https://lh4.googleusercontent.com/_TwtGvT0Ma-0/Tbqr0N7BjFI/AAAAAAAAADo/Sq-0hyQlhvE/orig.jpg](https://lh4.googleusercontent.com/_TwtGvT0Ma-0/Tbqr0N7BjFI/AAAAAAAAADo/Sq-0hyQlhvE/orig.jpg)
3-Level DWT is computed using db4 wavelet.
![https://lh6.googleusercontent.com/_TwtGvT0Ma-0/Tbqr57dIOrI/AAAAAAAAADs/TiNqMpscsD8/dwt.jpg](https://lh6.googleusercontent.com/_TwtGvT0Ma-0/Tbqr57dIOrI/AAAAAAAAADs/TiNqMpscsD8/dwt.jpg)
Perfect Reconstruction is achieved using idwt\_2d\_sym function.
![https://lh5.googleusercontent.com/_TwtGvT0Ma-0/Tbqr9ku8TJI/AAAAAAAAADw/yqE3StuDNmE/recon.jpg](https://lh5.googleusercontent.com/_TwtGvT0Ma-0/Tbqr9ku8TJI/AAAAAAAAADw/yqE3StuDNmE/recon.jpg)

184
2DSWTdemo.md Normal file
View File

@ -0,0 +1,184 @@
# 2D Stationary Wavelet Transform using swt\_2d #
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/demo/swt2Ddemo.cpp)
```
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <complex>
#include <cmath>
#include <algorithm>
#include "wavelet.h"
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
using namespace std;
using namespace cv;
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("cameraman.bmp");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
cvSaveImage("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
string nm = "db2";
// vector<double> l1,h1,l2,h2;
// filtcoef(nm,l1,h1,l2,h2);
vector<double> output;
int J =3;
swt_2d(vec1,J,nm,output);
cout << "OUTPUT size" << output.size() << endl;
cout << "LOOP OK" << endl;
int row,col;
dwt_output_dim(vec1, row, col );
// Extract and Display Low Pass Image at the Jth stage
vector<vector<double> > blur(row,vector<double>(col));
for (int i=0;i < row; i++){
for (int j=0; j < col;j++){
double temp = output[i*col + j];
blur[i][j]= temp;
}
}
double max;
maxval(blur,max);
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = col;
imgSize.height = row;
cvImg = cvCreateImage( imgSize, 8, 1 );
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( blur[i][j] <= 0.0){
blur[i][j] = 0.0;
}
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (blur[i][j] / max) * 255.0);
}
}
cvNamedWindow( "Low Pass Image", 1 ); // creation of a visualisation window
cvShowImage( "Low Pass Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("Low Pass Image");
// Displaying BandPass Images
vector<vector<double> > detail(3*row,vector<double>(J * col));
for (int k=0; k < J; k++) {
for (int i=0; i < 3*row; i++) {
for(int j=0+ k*col; j < (k+1)*col; j++) {
double temp = output[(3*k+1)*row*col+ i * col +j - k*col];
detail[i][j]= temp;
}
}
}
IplImage *dvImg; // image used for output
CvSize imgSz; // size of output image
imgSz.width = J*col;
imgSz.height = 3*row;
dvImg = cvCreateImage( imgSz, 8, 1 );
for (int i = 0; i < imgSz.height; i++ ) {
for (int j = 0; j < imgSz.width; j++ ){
if ( detail[i][j] <= 0.0){
detail[i][j] = 0.0;
}
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) detail[i][j];
}
}
cvNamedWindow( "Band Pass Image", 1 ); // creation of a visualisation window
cvShowImage( "Band Pass Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("Band Pass Image");
cvSaveImage("detail.bmp",dvImg);
return 0;
}
```
Stationary Wavelet Transform is a redundant transform as will be seen below. The image used is 256X256 grayscale "cameraman" image.
![https://lh4.googleusercontent.com/_TwtGvT0Ma-0/TbtFlJ28n6I/AAAAAAAAAFA/ffwmLZX8oRk/cameraman.jpg](https://lh4.googleusercontent.com/_TwtGvT0Ma-0/TbtFlJ28n6I/AAAAAAAAAFA/ffwmLZX8oRk/cameraman.jpg)
Three level Stationary Wavelet Transform is computed using db2 wavelet. Approximation coefficients are stored only for the final (J=3) stage while the three detail coefficients( Horizontal, Vertical and Diagonal) are stored for each value. All 10 sets of coefficients are 256X256.
Approximation Coefficient
![https://lh6.googleusercontent.com/_TwtGvT0Ma-0/Tbnv_x4dUbI/AAAAAAAAACk/9tvLG_-iZb4/apprx.jpg](https://lh6.googleusercontent.com/_TwtGvT0Ma-0/Tbnv_x4dUbI/AAAAAAAAACk/9tvLG_-iZb4/apprx.jpg)
Detail Coefficients at Levels 3,2,1. Coefficients are arranged Horizontal,Vertical and Diagonal from top to bottom.
![https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TbnvFEiRhpI/AAAAAAAAACc/doxXP9gpcl0/s640/detail.jpg](https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TbnvFEiRhpI/AAAAAAAAACc/doxXP9gpcl0/s640/detail.jpg)

Binary file not shown.

View File

@ -1,26 +0,0 @@
cmake_minimum_required(VERSION 3.15.2)
#
project(LIBWAVELET)
#
set(VERSION_MAJOR 1)
set(VERSION_MINOR 0)
#
add_subdirectory(src/)
# homebrew
set(CMAKE_INSTALL_PREFIX /usr/local)
# CPack
include (InstallRequiredSystemLibraries)
set(CPACK_OUTPUT_FILE_PREFIX "${PROJECT_SOURCE_DIR}/package")
#set(CPACK_RESOURCE_FILE_LICENSE "${CMAKE_CURRENT_SOURCE_DIR}/LICENSE")
set(CPACK_PACKAGE_VERSION_MAJOR "${VERSION_MAJOR}")
set(CPACK_PACKAGE_VERSION_MINOR "${VERSION_MINOR}")
#set(CPACK_PACKAGE_VERSION_PATCH "${VERSION_PATCH}")
set(PROJECT_VERSION_FULL ${VERSION_MAJOR}.${VERSION_MINOR})
set(CPACK_SOURCE_GENERATOR "TGZ")
set(CPACK_SOURCE_PACKAGE_FILE_NAME liblgd-${PROJECT_VERSION_FULL})
include (CPack)

340
COPYING
View File

@ -1,340 +0,0 @@
GNU GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1989, 1991 Free Software Foundation, Inc.
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. This
General Public License applies to most of the Free Software
Foundation's software and to any other program whose authors commit to
using it. (Some other Free Software Foundation software is covered by
the GNU Library General Public License instead.) You can apply it to
your programs, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must show them these terms so they know their
rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that redistributors of a free
program will individually obtain patent licenses, in effect making the
program proprietary. To prevent this, we have made it clear that any
patent must be licensed for everyone's free use or not licensed at all.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License applies to any program or other work which contains
a notice placed by the copyright holder saying it may be distributed
under the terms of this General Public License. The "Program", below,
refers to any such program or work, and a "work based on the Program"
means either the Program or any derivative work under copyright law:
that is to say, a work containing the Program or a portion of it,
either verbatim or with modifications and/or translated into another
language. (Hereinafter, translation is included without limitation in
the term "modification".) Each licensee is addressed as "you".
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running the Program is not restricted, and the output from the Program
is covered only if its contents constitute a work based on the
Program (independent of having been made by running the Program).
Whether that is true depends on what the Program does.
1. You may copy and distribute verbatim copies of the Program's
source code as you receive it, in any medium, provided that you
conspicuously and appropriately publish on each copy an appropriate
copyright notice and disclaimer of warranty; keep intact all the
notices that refer to this License and to the absence of any warranty;
and give any other recipients of the Program a copy of this License
along with the Program.
You may charge a fee for the physical act of transferring a copy, and
you may at your option offer warranty protection in exchange for a fee.
2. You may modify your copy or copies of the Program or any portion
of it, thus forming a work based on the Program, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) You must cause the modified files to carry prominent notices
stating that you changed the files and the date of any change.
b) You must cause any work that you distribute or publish, that in
whole or in part contains or is derived from the Program or any
part thereof, to be licensed as a whole at no charge to all third
parties under the terms of this License.
c) If the modified program normally reads commands interactively
when run, you must cause it, when started running for such
interactive use in the most ordinary way, to print or display an
announcement including an appropriate copyright notice and a
notice that there is no warranty (or else, saying that you provide
a warranty) and that users may redistribute the program under
these conditions, and telling the user how to view a copy of this
License. (Exception: if the Program itself is interactive but
does not normally print such an announcement, your work based on
the Program is not required to print an announcement.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Program,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Program, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Program.
In addition, mere aggregation of another work not based on the Program
with the Program (or with a work based on the Program) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may copy and distribute the Program (or a work based on it,
under Section 2) in object code or executable form under the terms of
Sections 1 and 2 above provided that you also do one of the following:
a) Accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of Sections
1 and 2 above on a medium customarily used for software interchange; or,
b) Accompany it with a written offer, valid for at least three
years, to give any third party, for a charge no more than your
cost of physically performing source distribution, a complete
machine-readable copy of the corresponding source code, to be
distributed under the terms of Sections 1 and 2 above on a medium
customarily used for software interchange; or,
c) Accompany it with the information you received as to the offer
to distribute corresponding source code. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form with such
an offer, in accord with Subsection b above.)
The source code for a work means the preferred form of the work for
making modifications to it. For an executable work, complete source
code means all the source code for all modules it contains, plus any
associated interface definition files, plus the scripts used to
control compilation and installation of the executable. However, as a
special exception, the source code distributed need not include
anything that is normally distributed (in either source or binary
form) with the major components (compiler, kernel, and so on) of the
operating system on which the executable runs, unless that component
itself accompanies the executable.
If distribution of executable or object code is made by offering
access to copy from a designated place, then offering equivalent
access to copy the source code from the same place counts as
distribution of the source code, even though third parties are not
compelled to copy the source along with the object code.
4. You may not copy, modify, sublicense, or distribute the Program
except as expressly provided under this License. Any attempt
otherwise to copy, modify, sublicense or distribute the Program is
void, and will automatically terminate your rights under this License.
However, parties who have received copies, or rights, from you under
this License will not have their licenses terminated so long as such
parties remain in full compliance.
5. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Program or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Program (or any work based on the
Program), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Program or works based on it.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the
original licensor to copy, distribute or modify the Program subject to
these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
7. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Program at all. For example, if a patent
license would not permit royalty-free redistribution of the Program by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Program.
If any portion of this section is held invalid or unenforceable under
any particular circumstance, the balance of the section is intended to
apply and the section as a whole is intended to apply in other
circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system, which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
8. If the distribution and/or use of the Program is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Program under this License
may add an explicit geographical distribution limitation excluding
those countries, so that distribution is permitted only in or among
countries not thus excluded. In such case, this License incorporates
the limitation as if written in the body of this License.
9. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of this License which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
this License, you may choose any version ever published by the Free Software
Foundation.
10. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to the public, the best way to achieve this is to make it
free software which everyone can redistribute and change under these terms.
To do so, attach the following notices to the program. It is safest
to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least
the "copyright" line and a pointer to where the full notice is found.
<one line to give the program's name and a brief idea of what it does.>
Copyright (C) <year> <name of author>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Also add information on how to contact you by electronic and paper mail.
If the program is interactive, make it output a short notice like this
when it starts in an interactive mode:
Gnomovision version 69, Copyright (C) year name of author
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the appropriate
parts of the General Public License. Of course, the commands you use may
be called something other than `show w' and `show c'; they could even be
mouse-clicks or menu items--whatever suits your program.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the program, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
`Gnomovision' (which makes passes at compilers) written by James Hacker.
<signature of Ty Coon>, 1 April 1989
Ty Coon, President of Vice
This General Public License does not permit incorporating your program into
proprietary programs. If your program is a subroutine library, you may
consider it more useful to permit linking proprietary applications with the
library. If this is what you want to do, use the GNU Library General
Public License instead of this License.

View File

@ -1,21 +0,0 @@
/*
* Copyright (c) 2011 Rafat Hussain
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.This program also uses FFTW3 library
* for high speed computation and it is being distributed in accordance
* with GNU-GPL license ver 2.0
* For FFTW3 copyright information, see the FFTW3 folder.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
*/

516
Functions.md Normal file
View File

@ -0,0 +1,516 @@
_Note : Only first ten functions are available in the wave1d library and convfft is also not included. It is my recommendation that you use the latest library(wavelet.lib and libwavelet.a in wavelet-03.rar) even for 1D operations as 1D implementation is faster and more accurate._
# 1D Functions #
### 1. J-Level Discrete Wavelet Transform ###
**`void* dwt(vector<double> &, int ,string , vector<double> &, vector<double> &)`**
Example Usage : **dwt(sig, J, nm, dwt\_output,flag )**
where,
**sig :** is the input signal . It is a `vector<double>` object.
**J :** Number of DWT Levels. Integer.
**nm :** Name of Wavelet. See function filtcoef for more information. String.
**dwt\_ouput:** is a `vector<double>` object that will return the DWT output.
**flag:** is a vector that contains two `vector<double>` values.
`flag[0]` - contains the number of zeros if the signal is zeropadded.
`flag[1]`- contains the number of decomposition levels. (J)
flag is used by IDWT to help process the DWT output.
Additional Outputs : In addition to above, the function also generates .txt and .dat files.
GNUPLOT ready .dat files
**gnusig.dat :** contains signal data
**gnufilt.dat:** Contains filters data.[Four filters are arranged columnwise in the file](All.md)
**gnuout.dat :** Contains DWT coefficients. It stores approximation and detail coefficients columnwise in alternating fashion. For example, three level of approximation and detail coefficients will result in gnuout.dat having 7 columns. First column is index followed by alternating approximation and detail columns.
Text Files : These two files are used by the code to generate gnuout.dat file.
**appx.txt :** Values of Approximation Coefficients from each stage. Values are appended after each stage.
**det.txt :** Values of Detail Coefficients after each stage. Values are likewise appended after each stage.
**dwtout.txt:** Stores the DWT ouput in text format. It contains Approximation coefficients at Jth level, followed by detail coefficients at Jthe, J-1,.... level 1.
**flag.txt:** Contains values of flags in text format.
### 2. 1-Level Discrete Wavelet Transform ###
**`void* dwt1(string, vector<double> &, vector<double> &, vector<double> &)`**
Example Usage: **dwt1(nm,sig, appx\_sig, det\_sig)**
**nm :** Wavelet Name. String
**sig :** Input Signal. `Vector<double>` Object.
**appx\_sig:** Approximation Coefficients. `Vector<double>` object.
**det\_sig:** Detail Coefficients. `Vector<double>` object.
Same Functionality can be achieved by setting J=1 in the dwt function but dwt1 directly outputs detail and approximation coefficients for one level of decomposition. This function will not generate any of GNUPLOT files but may be preferable in any number of scenarios.
### 3. Dyadic Zero-Padding ###
**`void* dyadic_zpad_1d(vector<double> &)`**
Example Usage: **dyadic\_zpad\_1d(sig)**
It zeropads signal sig such that its length is now dyadic. For example a signal with length 195 will be zeropadded to 256.
### 4. Convolution ###
Recommended -- **`double convfft(vector<double> &, vector<double> &, vector<double> &)`**
**-or-**
**`double convol(vector<double> &, vector<double> &, vector<double> &)`**
Example Usage: **convfft(signal,lpd,cA\_undec)**
where, signal and lpd are two inputs that are convolved and the convolution output is stored in cA\_undec. All three are `vector<double>` objects.
Important- **convfft** will not modify the value of signal while convol will. I have not corrected this as **convfft** is the faster, better implementation and should be used instead of **convol**.
### 5. Filter Coefficients ###
**`int filtcoef(string , vector<double> &, vector<double> &, vector<double> &, vector<double> &)`**
Example Usage: **filtcoef(nm,lpd,hpd,lpr,hpr)**
**nm:** Wavelet name.
**lpd:** Low Pass Decomposition Filter Coefficients.
**hpd:** High Pass Decomposition Filter Coefficients.
**lpr:** Low Pass Reconstruction Filter Coefficients.
**hpr:** High Pass Reconstruction Filter Coefficients.
All filters are `vector<double>` objects and can be obtained by specifying the wavelet name. Currently, following Wavelets are available:
Daubechies : db1,db2,.., ,db15
Biorthogonal: bior1.1 ,bior1.3 ,bior1.5 ,bior2.2 ,bior2.4 ,bior2.6 ,bior2.8 ,bior3.1 ,bior3.3 ,bior3.5 ,bior3.7 ,bior3.9 ,bior4.4 ,bior5.5 ,bior6.8
Coiflets: coif1,coif2,coif3,coif4,coif5
### 6. Downsampling ###
**`void downsamp(vector<double> &, int , vector<double> &)`**
Example Usage : **downsamp(cA\_undec, D, cA)**
**cA\_undec:** Signal to be downsampled. `Vector<double>`
**D :** Downsampling Factor. Integer
**cA:** Downsampled Signal. `Vector<double>`
### 7. Upsampling ###
**`void upsamp(vector<double> &, int, vector<double> &)`**
Example Usage : **upsamp(cA, U, cA\_up)**
**cA:** Signal to be upsampled. `Vector<double>`
**U :** Upsampling Factor. Integer
**cA\_up:** Upsampled Signal. `Vector<double>`
### 8. J-Level Inverse Discrete Wavelet Transform ###
**`void* idwt(vector<double> &,vector<double> &, string , vector<double> &)`**
Example Usage: **idwt(dwt\_output, flag,nm,output)**
**dwt\_output:** Output of DWT which serves as Input to the IDWT. `vector<double>`
**flag:** Contains values of J and zeropadding. `vector<double>`
**nm :** Wavelet name. String
**output:** Reconstructed IDWT Output. `vector<double>`
Additional .dat output
**gnurecon.dat :** GNUPLOT ready reconstructed signal.
### 9. 1-Level Inverse Discrete Wavelet Transform ###
**`void* idwt1(string wname, vector<double> &, vector<double> &, vector<double> &)`**
Example Usage : **idwt1(nm,idwt\_output, app,detail)**
**nm:** Wavelet Name.
**idwt\_output:** Outputs IDWT.
**app:** Approximation Coefficients.
**detail:** Detail Coefficients.
### 10. GNUDWTPLOT ###
**`void* gnudwtplot(int)`**
Example Usage: **gnudwtplot(J)**
Generates GNUPLOT script gnudwt.gnu.txt that contains plots of signals, filters and wavelet coefficients. it works if it is called following DWT and IDWT operations. To draw the plots, just load the script in gnuplot. See wavedemo1.cpp for more details.
# 1D Symmetric Extension DWT Functions #
### 11. J-Level Symmetric Extension DWT ###
**`void* dwt_sym(vector<double> &, int ,string , vector<double> &,vector<double> &,vector<int> &, int );`**
Example Usage: **dwt\_sym (signal, J,nm, dwt\_output, flag,length, e)**
Same as **dwt** function except it contains two more arguments and the output is a 1D vector. **length** is an integer vector which contains lengths of approximation and detail coefficients. **e** is the length of symmetric extension in each direction. **dwt\_output** stores coefficients in following format:
**`[A(J) D(J) D(J-1) ..... D(1)]`**
> where **A(J)** is the approximation coefficient vector at the Jth level while **D(n)** are the detail coefficient vectors at the nth level. **length** contains the lengths of corresponding vectors. Last entry of the **length** vector is the length of the original signal.
### 12. J-Level Symmetric Extension IDWT ###
**`void* idwt_sym(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);`**
Example Usage: **idwt\_sym(dwtop,flag,nm,idwt\_output,length)**
**idwt\_sym** is identical to **idwt** above except that it contains one more argument in lengths of the coefficients vector **length**. It is the same vector described in **11**.
### 13. Symmetric Extension ###
**`void* symm_ext(vector<double> &, int )`**
Example Usage: **symm\_ext(signal,e)**
**symm\_ext** symmetrically extends the signal by length e in either direction.
# 1D Stationary Wavelet Transform #
### 14. J-Level Stationary Wavelet Transform ###
**`void* swt(vector<double> &, int , string , vector<double> &, int &) `**
Example Usage: **swt(sig,J,nm,swt\_output,length)**
This function works on dyadic length signal. All the coefficients are of equal lengths and that value is stored in **length**. **swt\_output** stores value in the same format as **11** - Approximation coefficient vector at level J is stored at the beginning of the **swt\_output** vector followed by detail coefficients vectors at levels J, J-1,...., 1. Additionally, ALL coefficient vectors(including redundant approximation vectors) are stored in **gnuout.dat** file. See **gnuswtplot** for more details.
### 15. J-Level Inverse Stationary Wavelet Transform ###
**`void* iswt(vector<double> &,int , string, vector<double> &)`**
Example Usage: **iswt(swtop,J,nm,iswt\_output)**
**swtop** is the output of SWT stage , J - number of levels and nm is the wavelet as before. Output of ISWT is stored in **iswt\_output** vector.
### 16. GNUSWTPLOT ###
**`void* gnuswtplot(int)`**
Example Usage: **gnuswtplot(J)**
Generates GNUPLOT script gnudwt.gnu.txt that contains plots of signals, filters and wavelet coefficients. it works if it is called following SWT and ISWT operations. To draw the plots, just load the script in gnuplot.
### 17. 1D Periodic Extension ###
**`void* per_ext(vector<double> &, int )`**
Example Usage: **per\_ext(sig,a)**
**per\_ext** periodically extends the signal **sig** by value **a** in either direction.
# 2D Functions #
There are three sets of 2D DWT options.
1. Regular decimated 2D DWT and IDWT. It works with dyadic length 2D signals and outputs 2D signals.(The DWT output is in the format of a dyadically decomposed image with cLL, the low pass output, in the top left corner) If the input signal isn't of dyadic length then it will be zeropadded and you can calculate output size by using **dwt\_output\_dim** function and remove zeros from the output by using the **zero\_remove** function. More on this will follow. For a N X N dydadic length signal, the output is N X N which is useful in many applications.
![https://lh5.googleusercontent.com/_TwtGvT0Ma-0/Tbk_OaFazJI/AAAAAAAAABI/N9CQwURPJfs/ezw.png](https://lh5.googleusercontent.com/_TwtGvT0Ma-0/Tbk_OaFazJI/AAAAAAAAABI/N9CQwURPJfs/ezw.png)
2. Symmetric Extension 2D DWT and IDWT signal. It works with signal of any length and DWT output is a 1D vector (just as in Matlab) which may make it easier to handle in certain situations. On the flip side, the output is not of the same size as input and so there are some redundancies. To display the image, you'll have to convert 1D vector into image format and also account for downsampling and convolution which result in non-linear variation of length across deocmposition levels. The functions **dispDWT** and **dwt\_output\_dim\_sym** will help in displaying the image. On the flip side, performing operations on 1D
DWT output vector should be straightforward.
3. 2D Stationary Wavelet Transform. Inverse Stationary Transform is not implemented as of yet but 2d SWT should be good for image analysis, pattern recognition and edge detection operations that don't require ISWT for the most part.
### 18. J-Level 2D Discrete Wavelet Transform ###
**`void* dwt_2d(vector<vector<double> > &, int , string , vector<vector<double> > &, vector<double> &)`**
Example Usage: **dwt\_2d(vec1, J, nm, dwt\_output,flag )**
**vec1** is the 2D input signal.
**J** is the Decomposition level.
**nm** gives the name of wavelet family. See **filtcoef** for more details.
**dwt\_output** is the 2D output coefficients. They are arranged as shown in the figure above. The dimensions can be obtained by using **dwt\_output\_dim** function. A code fragment may look like this-
```
int rr1,cc1;
string nm = "db4";
// Finding DWT output dimensions as the DWT output is zeropadded
dwt_output_dim(vec1, rr1, cc1 );// vec1 is the input image/matrix
int J = 2;
vector<double> flag;// Flag stores values including size of input and level of decomposition and this vector needs to be passed to idwt_2d function.
vector<vector<double> > dwt_output(rr1, vector<double>(cc1));
// Computing 2d DWT ( vec1is the signal while dwt_output is the DWT output)
dwt_2d(vec1, J, nm, dwt_output,flag );
```
### 19. J-Level 2D Inverse Discrete Wavelet Transform ###
**`void* idwt_2d(vector<vector<double> > &,vector<double> &, string ,vector<vector<double> > &)`**
Example Usage: **idwt\_2d(dwt\_output,flag, nm ,idwt\_output)**
**idwt\_output** is a 2D vector object and may require zeropadding removal depending on the size of input image/matrix. Continuing from above, code fragment for IDWT may look like following
```
// Finding IDWT
vector<vector<double> > final(rr1, vector<double>(cc1));
idwt_2d(dwt_hold,flag, nm ,final);
// Removing Zeropadding
zero_remove(vec1,final);// vec1 is the input image/matrix
```
### 20. 2D Dyadic Zero Padding ###
**`void* dyadic_zpad_2d(vector<vector<double> > &,vector<vector<double> > &)`**
Example Usage: **dyadic\_zpad\_2d(sig,sig2)**
This function makes the signal of dyadic length by adding zeros. In this particular DWT implementation **dwt\_2d**, the output **sig2** will be a NXN matrix which may require a lot of zeros being padded to the signal. It may be desirable to use **dwt\_2d\_sym** function in this case which operates on images/matrices of any size without any zero-padding.
### 21. Get Output Dimension ###
**`void* dwt_output_dim(vector<vector<double> >&, int &, int & )`**
Example Usage: **dwt\_output\_dim(vec1, rr1, cc1 )**
Because of zero-padding, the output image may not be equal in size to the input image. This function returns the dimensions of output matrix. If you are using dyadic length image then output will have the same dimensions as the input. This function works only with **dwt\_2d** functions and not with other DWT implementations.
### 22. 2D Zeropad Removal ###
**`void* zero_remove(vector<vector<double> > &,vector<vector<double> > &) `**
Example Usage: **zero\_remove(vec1,final)**
**vec1** is the input signal while **final** is the zeropadded IDWT output. **zero\_remove** will remove zeros based on the size of the input image/matrix.
### 23. Get 2D DWT coefficients at level N ###
**`void* getcoeff2d(vector<vector<double> > &, vector<vector<double> > &,vector<vector<double> > &,vector<vector<double> > &,vector<double> &, int &)`**
Example Usage: **getcoeff2d(dwtoutput,cH,cV,cD,flag,N)**
Given 2D DWT output **dwtoutput** and the Nth level of decomposition, **getcoeff2d** will return the three detail coefficients at the Nth level of decomposition. Works only with **dwt\_2d** function.
### 24. 1-Level 2D DWT ###
**`void* dwt2(string ,vector<vector<double> > &, vector<vector<double> > &,vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &)`**
Example Usage: **dwt2(nm,sig,cA,cH,cV,cD)**
Given a 2D signal **sig** and wavelet name **nm**, **dwt2** will return the approximation(**cA**) and detail coefficients(**cH,cV,cD**) after 1 level of decomposition.
### 25. 1-Level 2D IDWT ###
**`void* idwt2(string ,vector<vector<double> > &, vector<vector<double> > &,vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &)`**
Example Usage: **idwt2(nm,idwt\_output, cA, cH,cV,cD)**
This is the exact inverse of **dwt2** function. Inputs are the four approximation and detail coefficients while the output is the singke stage **idwt\_output**.
### 26. 2D Downsampling ###
**`void* downsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int)`**
Example Usage: **downsamp2(vec1,vec2,rows\_dn,cols\_dn)**
**vec1** is the input, **rows\_dn** and **cols\_dn** are row and column downsampling factors. **vec2** is the downsampled matrix.
### 27. 2D Upsampling ###
**`void* upsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int)`**
Example Usage: **upsamp2(vec1,vec2,rows\_up,cols\_up)**
**vec1** is the input, **rows\_up** and **cols\_up** are row and column upsampling factors. **vec2** is the upsampled matrix.
# 2D Symmetric Extension DWT Functions #
### 28. J-Level Symmetric Extension 2D DWT ###
**`void* dwt_2d_sym(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,vector<int> &, int )`**
Example Usage: **dwt\_2d\_sym(vec1,J,nm,output,flag,length,e)**
**vec1** Input Image/Matrix
**J** Number of Decomposition Levels
**nm** Wavelet Name
**flag** Stores values for IDWT function
**output** 1D vector that stores the output in the following format
**`[A(J) D(J) D(J-1) ..... D(1)]`**
where **A(J)** is the approximation coefficient vector at the Jth level while **D(n)** are the detail coefficient vectors at the nth level. It is important to remember that approximation and detail coefficients are actually two dimensional so we need a length vector that stores rows and columns values of each coefficient element. The length vector is given by **length**.
For example, the first element of **output** vector is the approximation matrix stored as a vector and the first two elements of **length** vectors are row and column values of the approximation matrix. In other words, a 300 element approximation matrix ( 15 rows X 20 columns) can be extracted from the 300 element approximation vector.
**e** is the length of symmetric extension in all directions.
A code fragment is as following
```
string nm = "db4";
// Finding 2D DWT Transform of the image using symmetric extension algorithm
// Extension is set to 3 (eg., int e = 3)
vector<int> length;
vector<double> output,flag;
int J =3;
int e=3;
dwt_2d_sym(vec1,J,nm,output,flag,length,e);
```
This DWT implementation works on image/matrices of any size and no dyadic zero padding is required.
### 29. J-Level Symmetric Extension 2D IDWT ###
**`void* idwt_2d_sym(vector<double> &,vector<double> &, string ,vector<vector<double> > &,vector<int> &)`**
Example Usage: **idwt\_2d\_sym(dwt\_output,flag, nm, idwt\_output,length)**
**idwt\_output** will have the same dimensions as the input image/matrix.
```
// Finding IDWT
vector<vector<double> > idwt_output(rows, vector<double>(cols));// rows and cols are the rows and columns of the input image/matrix
idwt_2d_sym( output,flag, nm, idwt_output,length);
```
> For more on other arguments, see 28.
### 30. 2D Symmetric Extension ###
**`void symm_ext2d(vector<vector<double> > &,vector<vector<double> > &, int )`**
Example Usage: **symm\_ext2d(origsig,sig, ext)**
**origsig** is the original signal, **sig** is the extended signal. It is extended by integer value **ext** in all directions.
### 31. Additional dwt\_2d\_sym Functions ###
**`void* dispDWT(vector<double> &,vector<vector<double> > &, vector<int> &, vector<int> &, int )`**
and
**`void* dwt_output_dim_sym(vector<int> &,vector<int> &, int )`**
> As we mentioned previously,DWT output of symmetric extension 2D DWT is a one dimensional vector. Additionally, the output isn't of dyadic length across different decomposition levels which makes the rectangular display of DWT output image a bit challenging and imprecise. **dispDWT** and **dwt\_output\_dim\_sym** are two functions that are used to return a rectangular set of coefficients arranged to display the DWT in traditional format. A code fragment that computes symmetric DWT and then rearranges coefficients is shown next
```
string nm = "db4";
// Finding 2D DWT Transform of the image using symmetric extension algorithm
// Extension is set to 3 (eg., int e = 3)
vector<int> length;
vector<double> output,flag;
int J =3;
int e=3;
dwt_2d_sym(vec1,J,nm,output,flag,length,e);
vector<int> length2;
// This algorithm computes DWT of image of any given size. Together with convolution and
// subsampling operations it is clear that subsampled images are of different length than
// dyadic length images. In order to compute the "effective" size of DWT we do additional
// calculations.
dwt_output_dim_sym(length,length2,J);
// length2 gives the integer vector that contains the size of subimages that will
// combine to form the displayed output image. The last two entries of length2 gives the
// size of DWT ( rows_n by cols_n)
int siz = length2.size();
// The last two values of length2 vector give the dimensions of the DWT output.
int rows_n=length2[siz-2];
int cols_n = length2[siz-1];
vector<vector< double> > dwtdisp(rows_n, vector<double>(cols_n));
dispDWT(output,dwtdisp, length ,length2, J);
```
> There are ,obviously, other ways to display the DWT output. A more precise and more efficient way could be to display output separately at each level instead of trying to bruteforce them into one image.
# 2D Stationary Wavelet Transform Functions #
### 32. J-Level 2D Stationary Wavelet Transform ###
**`void* swt_2d(vector<vector<double> > &,int , string , vector<double> &)`**
Example Usage: **swt\_2d(vec1,J,nm,output)**
**output** is a 1D vector which is exactly equal to 1D DWT output vector of **dwt\_2d\_sym** except that in this case all coefficients are of same size. If **vec1** isn't a (2<sup>M)</sup> X (2<sup>M)</sup> image/matrix , it will be zeropadded to dyadic dimensions with rows = columns.
For example, a 3 level decomposition of 256X256 image yields 10 256X256 sets of coefficients - one approximation coefficient set at level 3 and three detail coefficients at each level.
![https://lh6.googleusercontent.com/_TwtGvT0Ma-0/Tbnv_x4dUbI/AAAAAAAAACk/9tvLG_-iZb4/apprx.jpg](https://lh6.googleusercontent.com/_TwtGvT0Ma-0/Tbnv_x4dUbI/AAAAAAAAACk/9tvLG_-iZb4/apprx.jpg)
_Approximation Coefficients at J=3 (256X256 Image)_
![https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TbnvFEiRhpI/AAAAAAAAACc/doxXP9gpcl0/s640/detail.jpg](https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TbnvFEiRhpI/AAAAAAAAACc/doxXP9gpcl0/s640/detail.jpg)
_Detail Coefficients at levels 3,2,1 respectively (768X768 image shown as 640X640)_
### 33. 2D Periodic Extension ###
**`void per_ext2d(vector<vector<double> > &,vector<vector<double> > &, int )`**
Example Usage: **per\_ext2d(origsig,sig, ext)**
**origsig** is the original signal, **sig** is the extended signal. It is extended by integer value **ext** in all directions.
# FFT Functions #
### 34. 1D FFT and IFFT ###
**`void* fft(vector<complex<double> > &,int ,unsigned int)`**
Example Usage: **fft(inp,1,N) -or- fft(inp,-1,N)**
**fft** performs in-place FFT operation on complex vector **inp**.
Second argument is 1 for forward FFT and -1 for Inverse FFT.
Third argument gives the length of the output. If N is larger than the length of **inp** then it will be zeropadded, FFT will be performed and N-length complex output will be returned.
### 35. Frequency Response ###
**`void* freq(vector<double> &, vector<double> &)`**
Example Usage: **freq(sig,fre\_oup)**
This function returns frequency response **fre\_oup** of signal **sig**. The function will also output a freq.dat file that can be directly plotted in GNUPLOT.

27
PageName.md Normal file
View File

@ -0,0 +1,27 @@
# 1D/2D Discrete Wavelet Transform Implementation in C++ #
1. 1D DWT and IDWT Implementation (Two Modes)
1. 2D DWT and IDWT Implementation (Two Modes)
1. 1D SWT and ISWT Implementation ( Stationary Wavelet Transform)
1. 2D SWT Implementation
1. Implemented using Danielson Lanczos FFT Algorithm
Libraries (Compiled using MinGW and MSVC++ 2010 compilers in Windows) are available in Downloads section while source code is available in the source "src" folder.
The libraries and source codes are available at http://code.google.com/p/wavelet1d/. I have tried to make this a more "user-friendly" implementation by keeping the functions as simple and descriptive as possible. Additionally, the 1D DWT/IDWT routines will output data that can be used easily with GNUPLOT. It causes redundancy and possibly some clutter if signal files are large but ,in my opinion, the trade-off is worth it. The accompanying script also works best only when DWT and IDWT routines are called in the same program.
I have used C++ vector objects to accept input, store and output data. This is done to overcome certain programming limitations associated with using arrays. Dynamic arrays were also an option but they require a lot of house-cleaning without having any advantages over vector objects. To learn more about vectors, please refer to excellent tutorial at http://www.cplusplus.com/reference/stl/vector/ Vectors and Arrays can be converted back and forth so even if you are more comfortable with arrays, using vectors should not really be a problem.
|**[List of Functions](http://code.google.com/p/wavelet1d/wiki/Functions)**| Lists all Functions available in the Library|
|:-------------------------------------------------------------------------|:--------------------------------------------|
|**[Example Code 1](http://code.google.com/p/wavelet1d/wiki/1DDWTdemo)**| 1D DWT/IDWT Demo Code|
|**[Example Code 2](http://code.google.com/p/wavelet1d/wiki/1DAppx)**| 1D Signal Approximation Demo|
|**[Example Code 3](http://code.google.com/p/wavelet1d/wiki/2DDWTdemo)**| 2D DWT/IDWT Demo Code|
|**[Example Code 4](http://code.google.com/p/wavelet1d/wiki/2DAppx)**| Image Approximation Demo|
|**[Example Code 5](http://code.google.com/p/wavelet1d/wiki/2DSWTdemo)**| 2D SWT Demo Code|
![https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TblVN_ieObI/AAAAAAAAACM/5l0NxJvA8XI/dwt.jpg](https://lh3.googleusercontent.com/_TwtGvT0Ma-0/TblVN_ieObI/AAAAAAAAACM/5l0NxJvA8XI/dwt.jpg)
_J=3 Level Discrete Wavelet Transform of a 486X486 image using dwt\_2d\_sym function_
Image Processing Note : I have not implemented any image class in C++ as of yet so I'm using OPENCV to handle images. It happens to be a rather bulky package and if you are not already working in image processing area, there are other more convenient options that may be used to handle simple image operations( loading, displaying, saving and converting them to c++ STL formats).

54
ProjectHome.md Normal file
View File

@ -0,0 +1,54 @@
# C++ 1D/2D DWT Implementation for Win32 and Linux #
### Wavelet2d / Wavelet2s Libraries ###
1. 1D DWT and IDWT Implementation (Two Modes)
1. 2D DWT and IDWT Implementation (Two Modes)
1. 1D SWT and ISWT Implementation ( Stationary Wavelet Transform)
1. 2D SWT Implementation
1. Implemented using FFTW3 Library
1. Shared(.so) and static(.a) libraries for Linux
1. Shared(.dll) and static(.a) libraries for Win32 GCC (MinGW).
1. Shared(.dll) libraries for Microsoft VC++
> This implementation uses C++ vector objects to accept input, store and output data. This is done to overcome certain programming limitations associated with using arrays. Dynamic arrays were also an option but they require a lot of house-cleaning without having any advantages over vector objects. To learn more about vectors, please refer to excellent tutorial at [CPLUSPLUS](http://www.cplusplus.com/reference/stl/vector/). Vectors and Arrays can be converted back and forth so even if you are more comfortable with arrays, using vectors should not really be a problem.
### Changes from Previous Version ###
Focus is on speed.
1. FFTW3 Library is used to improve computation speed.
2. No GNUPLOT outputs are generated.
3. Periodic and Symmetric functions take exactly same arguments unlike in previous versions. They will still be accessed by the same names, though.(dwt ,dwt\_sym etc.)
4. Focus on shared libraries. No static libraries for MSVC++ although MinGW and LINUX version will come with static as well as shared libraries.
5. These libraries work with signals or images of almost any size. Speed becomes an issue for very large images. Also click on "Issues" tab for more information on issues dealing with very small signal length.
6. Functions take different arguments as compared to previous versions and extensions are done based on length of filter so signal extension length is no longer an input value. See Lists of functions and example codes.
wavelet2d - dynamic libraries( .so.1.0 and .dll)
wavelet2s - static libraries (.a)
|**[Overview](http://code.google.com/p/wavelet1d/wiki/install)**| Working with Libraries|
|:--------------------------------------------------------------|:----------------------|
|**[List of Functions](http://code.google.com/p/wavelet1d/wiki/newfunc)**| Lists all Functions available in the wavelib Library|
|**[Example Code 1](http://code.google.com/p/wavelet1d/wiki/new1DDWTdemo)**| 1D DWT/IDWT Demo Code|
|**[Example Code 2](http://code.google.com/p/wavelet1d/wiki/new1DAppx)**| 1D Signal Approximation Demo|
|**[Example Code 3](http://code.google.com/p/wavelet1d/wiki/new2DDWTdemo)**| 2D DWT/IDWT Demo Code|
|**[Example Code 4](http://code.google.com/p/wavelet1d/wiki/new2DAppx)**| Image Approximation Demo|
|**[Example Code 5](http://code.google.com/p/wavelet1d/wiki/new2DSWTdemo)**| 2D SWT Demo|
|**[Example Code 6](http://code.google.com/p/wavelet1d/wiki/new1DSWTDemo)**| 1D SWT Demo Code|
|**[Previous Versions](http://code.google.com/p/wavelet1d/wiki/previous)**| Documentation (wavelet-03 and wavelet02 Libraries)|
|**[DyadWaves GUI](http://code.google.com/p/dyadwaves/)**| Open Source Wavelet GUI for Windows and Linux |
|**[Liftwave](http://code.google.com/p/liftwave/)**| An Alternative C++ Template based implementation of 1D/2D DWT using Lifting method|
![https://lh4.googleusercontent.com/-4w-fWQyoieo/Thn_s7qb8-I/AAAAAAAAAGs/B0HFvLru6CU/s512/empire.jpg](https://lh4.googleusercontent.com/-4w-fWQyoieo/Thn_s7qb8-I/AAAAAAAAAGs/B0HFvLru6CU/s512/empire.jpg)
_J=2 Level Discrete Wavelet Transform of a 569X800 image using dwt\_2d\_sym function (Resized here for Display)_
Image Processing Note : I have not implemented any image class in C++ so I'm using OPENCV to handle images. It happens to be a rather bulky package and if you are not already working in image processing area, there are other more convenient options that may be used to handle simple image operations( loading, displaying, saving and converting them to c++ STL formats).

View File

@ -1,21 +0,0 @@
# wavelet1d
Website : http://wavelet2d.sourceforge.net/
Preferred Download - https://sourceforge.net/projects/wavelet2d/files/wavelib-0.4.0.0/
Licensing and Dependencies -
These libraries are licensed under GNU-GPL v2.0 (or any later version). See COPYRIGHT and COPYING files for more information. These libraries statically and dynamically link to FFTW-3.2.2 static library, FFTW3-3.3 static libray and FFTw-3.2.2 dynamic libraries in different implementations. More information, fftw libraries and associated files for this version are available at www.fftw.org. I have not modified fftw source codes in any way shape or form so you may want to download copies of source code and other files from the FFTW website itself if you are so inclined.
Non FFTW Options - See the folders wavelib-nofftw and wavelib-nofftw-vs for options that don't need FFTW library. KissFFT is used instead. The latter option will work on visual studio.
Recommended Alternatives - A faster , completely self-contained implementation of 1D DWT,SWT and MODWT with BSD license is available at https://github.com/rafat/wavelib
Contact - rafat.hsn@gmail.com
## Edited By Yi Zhang
* Update to FFTW-3.3.8
* Move file from src to src_deprecated
* Copy files from src_MSVC to src

View File

@ -1 +0,0 @@
04/29/2010 : Libraries uploaded (See Downloads Section). Also check "Project Home" for Example codes.

View File

@ -1,192 +0,0 @@
//============================================================================
// Name : imagedemo1.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : 2D DWT and IDWT using OPENCV and a 512 by 512 grayscale image.
//============================================================================
#include <iostream>
#include <fstream>
#include <string>
#include <vector>
#include <cmath>
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
#include "wavelet.h"
using namespace std;
using namespace cv;
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
void* minval(vector<vector<double> > &arr, double &min){
min = 10000;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (min >= arr[i][j]){
min = arr[i][j];
}
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("lena512.bmp");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
cvSaveImage("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
int rr1,cc1;
string nm = "db4";
// Finding DWT output dimensions as the DWT output is zeropadded
dwt_output_dim(vec1, rr1, cc1 );
int J = 2;
vector<double> flag;
vector<vector<double> > dwt_output(rr1, vector<double>(cc1));
cout << rr1 << cc1 << "size of op" << endl;
// Computing 2d DWT ( vec1 is the signal while dwt_output is the DWT output)
dwt_2d(vec1, J, nm, dwt_output,flag );
cout << "dwt size" << dwt_output.size() << dwt_output[0].size() << endl;
double max,min;
maxval(dwt_output,max);
minval(dwt_output,min);
cout << "maxval" << max << " minval" << min << endl;
//Displaying Scaled Image
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = cc1;
imgSize.height = rr1;
cvImg = cvCreateImage( imgSize, 8, 1 );
// dwt_hold is created to hold the dwt output as further operations need to be
// carried out on dwt_output in order to display scaled images.
vector<vector<double> > dwt_hold(rr1, vector<double>(cc1));
dwt_hold = dwt_output;
// Setting coefficients of created image to the scaled DWT output values
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( dwt_output[i][j] <= 0.0){
dwt_output[i][j] = 0.0;
}
if ( i <= (imgSize.height/pow(2.0,double(J))) && j <= (imgSize.width/pow(2.0,double(J))) ) {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (dwt_output[i][j] / max) * 255.0);
} else {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) (dwt_output[i][j]) ;
}
}
}
cvNamedWindow( "DWT Image", 1 ); // creation of a visualisation window
cvShowImage( "DWT Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("DWT Image");
cvSaveImage("dwt.bmp",cvImg);
// Finding IDWT
vector<vector<double> > final(rr1, vector<double>(cc1));
idwt_2d(dwt_hold,flag, nm ,final);
// Removing Zeropadding
zero_remove(vec1,final);
//Displaying Reconstructed Image
IplImage *dvImg;
CvSize dvSize; // size of output image
dvSize.width = final[0].size();
dvSize.height = final.size();
dvImg = cvCreateImage( dvSize, 8, 1 );
for (int i = 0; i < dvSize.height; i++ )
for (int j = 0; j < dvSize.width; j++ )
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) (final[i][j]) ;
cvNamedWindow( "Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "Reconstructed Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("Reconstructed Image");
cvSaveImage("recon.bmp",dvImg);
ofstream diff("diff.dat");
for (unsigned int i=0; i < final.size(); i++) {
for (unsigned int j = 0; j < final[0].size(); j++) {
diff << final[i][j]-vec1[i][j] << " " ;
}
diff << endl;
}
ofstream recon("recon.dat");
for (unsigned int i=0; i < final.size(); i++) {
for (unsigned int j = 0; j < final[0].size(); j++) {
recon << (int)final[i][j] << " " ;
}
recon << endl;
}
ofstream orig("orig.dat");
for (unsigned int i=0; i < vec1.size(); i++) {
for (unsigned int j = 0; j < vec1[0].size(); j++) {
orig << (int)vec1[i][j] << " " ;
}
orig << endl;
}
return 0;
}

View File

@ -1,310 +0,0 @@
//============================================================================
// Name : imagedemo2.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : Image Approximation
//============================================================================
// IMPORTANT - Algorithm used to display Image is imprecise because of int 8 overflow issues
// and it shouldn't be used to judge the performance of the DWT. The DWT and IDWT outputs
// should be used for performance measurements. I have used maximum value rescaling to
// solve overflow issues and , obviously, it is going to result in suboptimal performance but
// it is good enough for demonstration purposes.
#include <iostream>
#include <fstream>
#include <string>
#include <vector>
#include <cmath>
#include <algorithm>
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
#include "wavelet.h"
using namespace std;
using namespace cv;
void findthresh(vector<double> &vector1, int N, double& t){
sort(vector1.begin(), vector1.end(), greater<double>());
t = vector1.at(N-1);
}
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
void* minval(vector<vector<double> > &arr, double &min){
min = 10000;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (min >= arr[i][j]){
min = arr[i][j];
}
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("lena512.bmp");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
int rr1,cc1;
string nm = "db3";
// Finding DWT output dimensions as the DWT output is zeropadded
dwt_output_dim(vec1, rr1, cc1 );
int J = 5;
vector<double> flag;
vector<vector<double> > dwt_output(rr1, vector<double>(cc1));
cout << rr1 << cc1 << "size of op" << endl;
// Computing 2d DWT ( vec1 is the signal while dwt_output is the DWT output)
dwt_2d(vec1, J, nm, dwt_output,flag );
cout << "dwt size" << dwt_output.size() << dwt_output[0].size() << endl;
double max,min;
maxval(dwt_output,max);
minval(dwt_output,min);
cout << "maxval" << max << " minval" << min << endl;
vector<vector<double> > dwt_coef1(rr1, vector<double>(cc1));
vector<vector<double> > dwt_coef2(rr1, vector<double>(cc1));
// Storing dwt_output for two different computations based on
// different approximation values
dwt_coef1 = dwt_output;
dwt_coef2 = dwt_output;
//Displaying Scaled Image
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = cc1;
imgSize.height = rr1;
cvImg = cvCreateImage( imgSize, 8, 1 );
// Setting coefficients of created image to the scaled DWT output values
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( dwt_output[i][j] <= 0.0){
dwt_output[i][j] = 0.0;
}
if ( i <= (imgSize.height/pow(2.0,double(J))) && j <= (imgSize.width/pow(2.0,double(J))) ) {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (dwt_output[i][j] / max) * 255.0);
} else {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) (dwt_output[i][j]) ;
}
}
}
// IMPORTANT -- dwt_output value has been modified above.
cvNamedWindow( "DWT Image", 1 ); // creation of a visualisation window
cvShowImage( "DWT Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("DWT Image");
// Case 1 : Only 10% of the largest coefficients are considered
// Total elements in the original image is rows * cols
int n_coef1= int (( rows * cols)/ 10);
// Finding Threshold Value corresponding to n_coef1
vector<double> temp1;
cout << "size: " << (int) temp1.size() << "\n";
cout << "capacity: " << (int) temp1.capacity() << "\n";
cout << "max_size: " << (int) temp1.max_size() << "\n";
for (int i =0; i < rr1; i++) {
for (int j = 0; j < cc1; j++){
double tempval = abs(dwt_coef1[i][j]);
temp1.push_back(tempval);
}
}
double thresh1= 0.0;
findthresh(temp1,n_coef1,thresh1);
ofstream temp("temp.txt");
for (int i =0; i < rows * cols; i++){
temp << temp1[i] << " " ;
}
// Reset coeffficients value depending on threshold value
for (int i =0; i < rr1; i++) {
for (int j = 0; j < cc1; j++){
double temp = abs(dwt_coef1[i][j]);
if (temp < thresh1){
dwt_coef1[i][j] = 0.0;
}
}
}
// Finding IDWT
vector<vector<double> > final(rr1, vector<double>(cc1));
idwt_2d(dwt_coef1,flag, nm ,final);
// Removing Zeropadding
zero_remove(vec1,final);
double max1;
maxval(final,max1);
//Displaying Reconstructed Image
IplImage *dvImg;
CvSize dvSize; // size of output image
dvSize.width = final[0].size();
dvSize.height = final.size();
dvImg = cvCreateImage( dvSize, 8, 1 );
for (int i = 0; i < dvSize.height; i++ ) {
for (int j = 0; j < dvSize.width; j++ ){
if ( final[i][j] <= 0.0){
final[i][j] = 0.0;
}
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) ((final[i][j]/max1) * 255) ;
}
}
cvNamedWindow( "10% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "10% Coeff Reconstructed Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("10% Coeff Reconstructed Image");
// Case 2 : Only 2% of the largest coefficients are considered
// Total elements in the original image is rows * cols
int n_coef2= int (( rows * cols) / 50);
// Finding Threshold Value corresponding to n_coef1
vector<double> temp2;
for (int i =0; i < rr1; i++) {
for (int j = 0; j < cc1; j++){
double tempval = abs(dwt_coef2[i][j]);
temp2.push_back(tempval);
}
}
double thresh2= 0.0;
findthresh(temp2,n_coef2,thresh2);
// Reset coeffficients value depending on threshold value
for (int i =0; i < rr1; i++) {
for (int j = 0; j < cc1; j++){
double temp = abs(dwt_coef2[i][j]);
if (temp < thresh2){
dwt_coef2[i][j] = 0.0;
}
}
}
// Finding IDWT
vector<vector<double> > final2(rr1, vector<double>(cc1));
idwt_2d(dwt_coef2,flag, nm ,final2);
// Removing Zeropadding
zero_remove(vec1,final2);
double max2;
maxval(final2,max2);
//Displaying Reconstructed Image
IplImage *dvImg2;
CvSize dvSize2; // size of output image
dvSize2.width = final2[0].size();
dvSize2.height = final2.size();
dvImg2 = cvCreateImage( dvSize2, 8, 1 );
for (int i = 0; i < dvSize2.height; i++ ) {
for (int j = 0; j < dvSize2.width; j++ ){
if ( final2[i][j] <= 0.0){
final2[i][j] = 0.0;
}
((uchar*)(dvImg2->imageData + dvImg2->widthStep*i))[j] =
(char) ((final2[i][j]/ max2)* 255) ;
}
}
cvNamedWindow( "2% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "2% Coeff Reconstructed Image", dvImg2 ); // image visualisation
cvWaitKey();
cvDestroyWindow("2% Coeff Reconstructed Image");
cout << thresh1 << " " << thresh2 << endl;
return 0;
}

View File

@ -1,204 +0,0 @@
//============================================================================
// Name : imagedemo_sym.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : DWT of arbitrary size image using symmetric extension
//============================================================================
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <complex>
#include <cmath>
#include <algorithm>
#include "wavelet.h"
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
using namespace std;
using namespace cv;
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
void* maxval1(vector<double> &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
if (max <= arr[i]){
max = arr[i];
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("Fig10.04(a).jpg");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
cvSaveImage("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
string nm = "db3";
vector<double> l1,h1,l2,h2;
filtcoef(nm,l1,h1,l2,h2);
// unsigned int lf=l1.size();
// int rows_n =(int) (rows+ J*(lf-1));
// int cols_n =(int) (cols + J * ( lf -1));
// Finding 2D DWT Transform of the image using symetric extension algorithm
// Extension is set to 3 (eg., int e = 3)
vector<int> length;
vector<double> output,flag;
int J =3;
int e=3;
dwt_2d_sym(vec1,J,nm,output,flag,length,e);
double max;
vector<int> length2;
// This algorithm computes DWT of image of any given size. Together with convolution and
// subsampling operations it is clear that subsampled images are of different length than
// dyadic length images. In order to compute the "effective" size of DWT we do additional
// calculations.
dwt_output_dim_sym(length,length2,J);
// length2 is gives the integer vector that contains the size of subimages that will
// combine to form the displayed output image. The last two entries of length2 gives the
// size of DWT ( rows_n by cols_n)
int siz = length2.size();
int rows_n=length2[siz-2];
int cols_n = length2[siz-1];
vector<vector< double> > dwtdisp(rows_n, vector<double>(cols_n));
dispDWT(output,dwtdisp, length ,length2, J);
// dispDWT returns the 2D object dwtdisp which will be displayed using OPENCV's image
// handling functions
vector<vector<double> > dwt_output= dwtdisp;
maxval(dwt_output,max);// max value is needed to take care of overflow which happens because
// of convolution operations performed on unsigned 8 bit images
//Displaying Scaled Image
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = cols_n;
imgSize.height = rows_n;
cvImg = cvCreateImage( imgSize, 8, 1 );
// dwt_hold is created to hold the dwt output as further operations need to be
// carried out on dwt_output in order to display scaled images.
vector<vector<double> > dwt_hold(rows_n, vector<double>( cols_n));
dwt_hold = dwt_output;
// Setting coefficients of created image to the scaled DWT output values
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( dwt_output[i][j] <= 0.0){
dwt_output[i][j] = 0.0;
}
if ( i <= (length2[0]) && j <= (length2[1]) ) {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (dwt_output[i][j] / max) * 255.0);
} else {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) (dwt_output[i][j]) ;
}
}
}
cvNamedWindow( "DWT Image", 1 ); // creation of a visualisation window
cvShowImage( "DWT Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("DWT Image");
cvSaveImage("dwt.bmp",cvImg);
// Finding IDWT
vector<vector<double> > idwt_output(rows, vector<double>(cols));
idwt_2d_sym( output,flag, nm, idwt_output,length);
//Displaying Reconstructed Image
IplImage *dvImg;
CvSize dvSize; // size of output image
dvSize.width = idwt_output[0].size();
dvSize.height = idwt_output.size();
cout << idwt_output.size() << idwt_output[0].size() << endl;
dvImg = cvCreateImage( dvSize, 8, 1 );
for (int i = 0; i < dvSize.height; i++ )
for (int j = 0; j < dvSize.width; j++ )
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) (idwt_output[i][j]) ;
cvNamedWindow( "Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "Reconstructed Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("Reconstructed Image");
cvSaveImage("recon.bmp",dvImg);
return 0;
}

View File

@ -1,342 +0,0 @@
//============================================================================
// Name : imagedemo_sym2.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : Image Approximation using symmetric extension 2D DWT
//============================================================================
// IMPORTANT - Algorithm used to display Image is imprecise because of int 8 overflow issues
// and it shouldn't be used to judge the performance of the DWT. The DWT and IDWT outputs
// should be used for performance measurements. I have used maximum value rescaling to
// solve overflow issues and , obviously, it is going to result in suboptimal performance but
// it is good enough for demonstration purposes.
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <complex>
#include <cmath>
#include <algorithm>
#include "wavelet.h"
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
using namespace std;
using namespace cv;
void findthresh(vector<double> &vector1, int N, double& t){
sort(vector1.begin(), vector1.end(), greater<double>());
t = vector1.at(N-1);
}
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
void* maxval1(vector<double> &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
if (max <= arr[i]){
max = arr[i];
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("lena512.bmp");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
cvSaveImage("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
string nm = "db2";
vector<double> l1,h1,l2,h2;
filtcoef(nm,l1,h1,l2,h2);
// unsigned int lf=l1.size();
// int rows_n =(int) (rows+ J*(lf-1));
// int cols_n =(int) (cols + J * ( lf -1));
// Finding 2D DWT Transform of the image using symetric extension algorithm
// Extension is set to 0 (eg., int e = 0)
vector<int> length;
vector<double> output,flag;
int J =6;
int e=0;
dwt_2d_sym(vec1,J,nm,output,flag,length,e);
double max;
vector<int> length2;
// This algorithm computes DWT of image of any given size. Together with convolution and
// subsampling operations it is clear that subsampled images are of different length than
// dyadic length images. In order to compute the "effective" size of DWT we do additional
// calculations.
dwt_output_dim_sym(length,length2,J);
// length2 is gives the integer vector that contains the size of subimages that will
// combine to form the displayed output image. The last two entries of length2 gives the
// size of DWT ( rows_n by cols_n)
int siz = length2.size();
int rows_n=length2[siz-2];
int cols_n = length2[siz-1];
vector<vector< double> > dwtdisp(rows_n, vector<double>(cols_n));
dispDWT(output,dwtdisp, length ,length2, J);
// dispDWT returns the 2D object dwtdisp which will be displayed using OPENCV's image
// handling functions
vector<vector<double> > dwt_output= dwtdisp;
// Stroing the DWT coefficients in two different vectors that will be used to approximate
// Image with two different sets of chosen coefficients.
vector<double> dwt_coef1;
vector<double> dwt_coef2;
dwt_coef1 = output;
dwt_coef2 = output;
maxval(dwt_output,max);// max value is needed to take care of overflow which happens because
// of convolution operations performed on unsigned 8 bit images
//Displaying Scaled Image
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = cols_n;
imgSize.height = rows_n;
cvImg = cvCreateImage( imgSize, 8, 1 );
// dwt_hold is created to hold the dwt output as further operations need to be
// carried out on dwt_output in order to display scaled images.
vector<vector<double> > dwt_hold(rows_n, vector<double>( cols_n));
dwt_hold = dwt_output;
// Setting coefficients of created image to the scaled DWT output values
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( dwt_output[i][j] <= 0.0){
dwt_output[i][j] = 0.0;
}
if ( i <= (length2[0]) && j <= (length2[1]) ) {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (dwt_output[i][j] / max) * 255.0);
} else {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) (dwt_output[i][j]) ;
}
}
}
cvNamedWindow( "DWT Image", 1 ); // creation of a visualisation window
cvShowImage( "DWT Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("DWT Image");
cvSaveImage("dwt.bmp",cvImg);
// Case 1 : Only 10% of the largest coefficients are considered
// Output is the 1D DWT vector
int n_coef1= int (output.size()/ 10);
cout << n_coef1 << endl;
// Finding Threshold Value corresponding to n_coef1
vector<double> temp1;
cout << "size: " << (int) temp1.size() << "\n";
cout << "capacity: " << (int) temp1.capacity() << "\n";
cout << "max_size: " << (int) temp1.max_size() << "\n";
for (unsigned int i =0; i < dwt_coef1.size(); i++) {
double tempval = abs(dwt_coef1[i]);
temp1.push_back(tempval);
}
double thresh1= 0.0;
findthresh(temp1,n_coef1,thresh1);
cout << "thresh" << thresh1 << endl;
ofstream temp("temp.txt");
for (unsigned int i =0; i < temp1.size(); i++){
temp << temp1[i] << " " ;
}
// Reset coeffficients value depending on threshold value
for (unsigned int i =0; i < dwt_coef1.size(); i++) {
double temp = abs(dwt_coef1[i]);
if (temp < thresh1){
dwt_coef1.at(i)= 0.0;
}
}
// Finding IDWT
vector<vector<double> > idwt_output(rows, vector<double>(cols));
idwt_2d_sym( dwt_coef1,flag, nm, idwt_output,length);
double max1;
maxval(idwt_output,max1);
//Displaying Reconstructed Image
IplImage *dvImg;
CvSize dvSize; // size of output image
dvSize.width = idwt_output[0].size();
dvSize.height = idwt_output.size();
cout << idwt_output.size() << idwt_output[0].size() << endl;
dvImg = cvCreateImage( dvSize, 8, 1 );
for (int i = 0; i < dvSize.height; i++ ){
for (int j = 0; j < dvSize.width; j++ ){
if ( idwt_output[i][j] <= 0.0){
idwt_output[i][j] = 0.0;
}
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) ((idwt_output[i][j] / max1) * 255 ) ;
}
}
cvNamedWindow( "10% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "10% Coeff Reconstructed Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("10% Coeff Reconstructed Image");
cvSaveImage("recon.bmp",dvImg);
// Case 2 : Only 2% of the largest coefficients are considered
// Output is the 1D DWT vector
int n_coef2= int (output.size()/ 50);
cout << n_coef2 << endl;
// Finding Threshold Value corresponding to n_coef1
vector<double> temp2;
for (unsigned int i =0; i < dwt_coef2.size(); i++) {
double tempval = abs(dwt_coef2[i]);
temp2.push_back(tempval);
}
double thresh2= 0.0;
findthresh(temp2,n_coef2,thresh2);
cout << "thresh" << thresh2 << endl;
// Reset coeffficients value depending on threshold value
for (unsigned int i =0; i < dwt_coef2.size(); i++) {
double temp = abs(dwt_coef2[i]);
if (temp < thresh2){
dwt_coef2.at(i)= 0.0;
}
}
// Finding IDWT
vector<vector<double> > idwt_output2(rows, vector<double>(cols));
idwt_2d_sym( dwt_coef2,flag, nm, idwt_output2,length);
double max2;
maxval(idwt_output2,max2);
//Displaying Reconstructed Image
IplImage *dvImg2;
CvSize dvSize2; // size of output image
dvSize2.width = idwt_output2[0].size();
dvSize2.height = idwt_output2.size();
cout << idwt_output2.size() << idwt_output2[0].size() << endl;
dvImg2 = cvCreateImage( dvSize2, 8, 1 );
for (int i = 0; i < dvSize2.height; i++ ) {
for (int j = 0; j < dvSize2.width; j++ ) {
if ( idwt_output2[i][j] <= 0.0){
idwt_output2[i][j] = 0.0;
}
((uchar*)(dvImg2->imageData + dvImg2->widthStep*i))[j] =
(char) ((idwt_output2[i][j]/ max2) * 255 ) ;
}
}
cvNamedWindow( "2% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "2% Coeff Reconstructed Image", dvImg2 ); // image visualisation
cvWaitKey();
cvDestroyWindow("2% Coeff Reconstructed Image");
cvSaveImage("recon2.bmp",dvImg2);
return 0;
}

View File

@ -1 +0,0 @@
-18.3237 -18.2232 -18.0974 -17.9410 -17.7480 -17.5113 -17.2230 -16.8744 -16.4558 -15.9565 -15.3653 -14.6701 -13.8586 -12.9182 -11.8363 -10.6008 -9.2006 -7.6257 -5.8680 -3.9217 -1.7839 0.5452 3.0614 5.7562 8.6167 11.6252 14.7591 17.9909 21.2884 24.6155 27.9319 31.1947 34.3587 37.3775 40.2049 42.7957 13.2164 14.2125 15.0317 15.6595 16.0845 16.2990 16.2990 16.0845 15.6595 15.0317 14.2125 13.2164 12.0608 10.7654 9.3517 34.3587 31.1947 27.9319 24.6155 21.2884 17.9909 14.7591 11.6252 8.6167 5.7562 3.0614 0.5452 -1.7839 -3.9217 -5.8680 -7.6257 -9.2006 -10.6008 -11.8363 -12.9182 -13.8586 -14.6701 -15.3653 -15.9565 -16.4558 -16.8744 -17.2230 -17.5113 -17.7480 -17.9410 -18.0974 -18.2232 -18.3237 -18.4035 -18.0080 -17.8889 -17.7403 -17.5533 -17.3156 -17.0102 -16.6129 -16.0884 -15.3848 -14.4239 -13.0840 -11.1708 -8.3634 -4.1098 2.5833 13.6048 32.7934 28.0187 10.9660 1.0776 -4.9459 -8.7354 -11.1225 -12.4865 -12.8019 -11.2050 -3.3124 1.8995 -11.3573 -15.0684 -16.5028 -17.1937 -17.5831 -17.8288 -17.9968 -18.1185 -18.2103 -18.2818 -18.3388 -18.3849 -18.4229 -18.4545 -18.4810 -17.4642 -17.2104 -16.9033 -16.5317 -16.0822 -15.5384 -14.8804 -14.0844 -13.1214 -11.9563 -10.5467 -8.8414 -6.7782 -4.2822 -1.2624 2.3911 6.8111 12.1585 18.6280 26.4549 35.9241 35.9241 26.4549 18.6280 12.1585 6.8111 2.3911 -1.2624 -4.2822 -6.7782 -8.8414 -10.5467 -11.9563 -13.1214 -14.0844 -14.8804 -15.5384 -16.0822 -16.5317 -16.9033 -17.2104 -17.4642 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 34.8066 34.6752 34.5285 34.3645 34.1812 33.9763 33.7474 33.4917 33.2058 32.8863 32.5294 32.1304 31.6846 31.1864 30.6296 30.0074 29.3121 28.5350 27.6667 26.6963 25.6118 24.3999 23.0456 21.5322 19.8408 17.9507 15.8385 13.4781 10.8403 7.8925 4.5982 0.9168 -3.1972 -7.7947 -12.9325 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.3237

View File

@ -1,172 +0,0 @@
//============================================================================
// Name : swt2Ddemo.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : 2D SWT Demo using OPENCV
//============================================================================
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <complex>
#include <cmath>
#include <algorithm>
#include "wavelet.h"
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
using namespace std;
using namespace cv;
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("cameraman.bmp");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
cvSaveImage("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
string nm = "db2";
// vector<double> l1,h1,l2,h2;
// filtcoef(nm,l1,h1,l2,h2);
vector<double> output;
int J =3;
swt_2d(vec1,J,nm,output);
cout << "OUTPUT size" << output.size() << endl;
cout << "LOOP OK" << endl;
int row,col;
dwt_output_dim(vec1, row, col );
// Extract and Display Low Pass Image at the Jth stage
vector<vector<double> > blur(row,vector<double>(col));
for (int i=0;i < row; i++){
for (int j=0; j < col;j++){
double temp = output[i*col + j];
blur[i][j]= temp;
}
}
double max;
maxval(blur,max);
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = col;
imgSize.height = row;
cvImg = cvCreateImage( imgSize, 8, 1 );
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( blur[i][j] <= 0.0){
blur[i][j] = 0.0;
}
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (blur[i][j] / max) * 255.0);
}
}
cvNamedWindow( "Low Pass Image", 1 ); // creation of a visualisation window
cvShowImage( "Low Pass Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("Low Pass Image");
// Displaying BandPass Images
vector<vector<double> > detail(3*row,vector<double>(J * col));
for (int k=0; k < J; k++) {
for (int i=0; i < 3*row; i++) {
for(int j=0+ k*col; j < (k+1)*col; j++) {
double temp = output[(3*k+1)*row*col+ i * col +j - k*col];
detail[i][j]= temp;
}
}
}
IplImage *dvImg; // image used for output
CvSize imgSz; // size of output image
imgSz.width = J*col;
imgSz.height = 3*row;
dvImg = cvCreateImage( imgSz, 8, 1 );
for (int i = 0; i < imgSz.height; i++ ) {
for (int j = 0; j < imgSz.width; j++ ){
if ( detail[i][j] <= 0.0){
detail[i][j] = 0.0;
}
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) detail[i][j];
}
}
cvNamedWindow( "Band Pass Image", 1 ); // creation of a visualisation window
cvShowImage( "Band Pass Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("Band Pass Image");
cvSaveImage("detail.bmp",dvImg);
return 0;
}

View File

@ -1,74 +0,0 @@
//============================================================================
// Name : swtdemo.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : 1D Stationary Wavelet Transform Demo
//============================================================================
#include <iostream>
#include <fstream>
#include "wavelet.h"
#include <vector>
#include <string>
#include <cmath>
using namespace std;
int main() {
cout << "********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********" << endl; // prints
cout << "This program accepts signal from the user in a file format " << endl;
cout << "and performs Discrete Wavelet Transform with specified " << endl;
cout << "wavelet. " << endl;
cout << " " << endl;
cout << " The Following Wavelets are in the Database: " << endl;
cout << " haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10, " << endl;
cout << " db11, db12, db13, db14, db15. " << endl;
cout << " bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8, " << endl;
cout << " bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4," << endl;
cout << " bior5.5, bior6.8." << endl;
cout << " coif1, coif2, coif3, coif4, coif5." << endl;
cout << "Please Enter the Wavelet Name at the Prompt( No quotes) :" << endl;
string nm; // nm will store the name of Wavelet Family
cin >> nm;
cout << "Enter the name of signal file at the Prompt eg., signal.txt :" << endl;
char inp[50];
cin >> inp;
vector<double> sig;
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
exit(1);
}
while (sig_inp) {
double temp;
sig_inp >> temp;
sig.push_back(temp);
}
sig.pop_back();
vector<double> original;
original = sig; // Make a copy of the signal if you want to use original signal
// later on. The other option is to use IDWT output as the SWt/ISWT system is
// Perefect Reconstruction system.
cout << "Please Enter the Number of DWT Stages J :" << endl;
int J;
cin >> J ;
vector<double> swt_output;
// perform J-Level DWT
int length;// All coefficients are of same length. Variable "length" returns length
// of coefficients. It is not required for ISWT computations.
// If signal is not of dyadic length it is zeropadded as the algorithm is designed to
// work with signals of 2^M length. These extra zeros can be removed after reconstruction.
swt(sig, J, nm, swt_output, length);
vector<double> iswt_output;
iswt(swt_output,J, nm,iswt_output);
gnuswtplot(J);
return 0;
}

View File

@ -1,524 +0,0 @@
void* iswt_2d(vector<double> &swtop,int J, string nm, vector<vector<double> > &sig,int row, int col) {
// 2D Inverse Stationary Wavelet Transform
// Works In Conjunction with C++ Wavelet Library http://code.google.com/p/wavelet1d/
// (C) Rafat Hussain under GNU GPL v3
// See Project page http://code.google.com/p/wavelet1d/
// swtop [1D Output vector from swt_2d]
// J [Number of Levels]
// nm [Wavelet Name]
// sig [Output]
// row & col [Rows and cols of sig]
// I have not fully tested this code.
// References :
// 1. Nason, G.P. and Silverman, B.W. (1995) The stationary wavelet transform and some statistical applications.
// In Antoniadis, A. and Oppenheim, G. (eds) Lecture Notes in Statistics, 103, 281--300.
// 2. Pesquet, J.C.; H. Krim, H. Carfatan (1996), "Time-invariant orthonormal wavelet representations,"
// http://pdf.aminer.org/000/318/848/frequency_shift_invariant_orthonormal_wavelet_packet_representations.pdf
int rows_n =row;
int cols_n = col;
vector<double> lp1,hp1,lp2,hp2;
filtcoef(nm,lp1,hp1,lp2,hp2);
vector<double> low_pass = lp2;
vector<double> high_pass = hp2;
int lf = low_pass.size();
int sum =0;
vector<vector<double> > cLL(rows_n, vector<double>(cols_n));
for (int iter=J; iter > 0; iter--) {
vector<vector<double> > cLH(rows_n, vector<double>(cols_n));
vector<vector<double> > cHL(rows_n, vector<double>(cols_n));
vector<vector<double> > cHH(rows_n, vector<double>(cols_n));
if (iter == J) {
for (int i = 0 ; i < rows_n; i++ ){
for (int j = 0; j < cols_n; j++){
cLL[i][j] = swtop[sum+ i * cols_n + j];
cHL[i][j] = swtop[sum+ rows_n * cols_n+ i * cols_n + j];
cLH[i][j] = swtop[sum+ 2 * rows_n * cols_n + i * cols_n + j];
cHH[i][j] = swtop[sum+ 3* rows_n * cols_n + i * cols_n + j];
}
}
sum+= 4 * rows_n * cols_n;
} else {
for (int i = 0 ; i < rows_n; i++ ){
for (int j = 0; j < cols_n; j++){
cHL[i][j] = swtop[sum+ i * cols_n + j];
cLH[i][j] = swtop[sum+ rows_n * cols_n + i * cols_n + j];
cHH[i][j] = swtop[sum+ 2* rows_n * cols_n + i * cols_n + j];
}
}
sum+= 3 * rows_n * cols_n;
}
int value = (int) pow(2.0,(double) (iter-1));
for (int count = 0; count < value; count++) {
vector<vector<double> > cLL1(rows_n/value, vector<double>(cols_n/value));
vector<vector<double> > cLH1(rows_n/value, vector<double>(cols_n/value));
vector<vector<double> > cHL1(rows_n/value, vector<double>(cols_n/value));
vector<vector<double> > cHH1(rows_n/value, vector<double>(cols_n/value));
int row1 = 0;
int col1 = 0;
for (int index_r = count; index_r < rows_n; index_r+=value){
for (int index_c = count; index_c < cols_n; index_c+=value){
cLL1[row1][col1]=cLL[index_r][index_c];
cLH1[row1][col1]=cLH[index_r][index_c];
cHL1[row1][col1]=cHL[index_r][index_c];
cHH1[row1][col1]=cHH[index_r][index_c];
col1++;
}
col1 = 0;
row1++;
}
//Implementing shift =0
unsigned int len_c = cLL1[0].size();
unsigned int len_r = cLL1.size();
vector<vector<double> > cL(rows_n,vector<double>(cols_n));
vector<vector<double> > cH(rows_n,vector<double>(cols_n));
vector<vector<double> > cLL2(len_r/2, vector<double>(len_c/2));
vector<vector<double> > cLH2(len_r/2, vector<double>(len_c/2));
vector<vector<double> > cHL2(len_r/2, vector<double>(len_c/2));
vector<vector<double> > cHH2(len_r/2, vector<double>(len_c/2));
row1=0;
col1=0;
for (int index_r = 0; index_r < len_r; index_r+=2){
for (unsigned int index_c = 0; index_c < len_c; index_c+=2){
cLL2[row1][col1]=cLL1[index_r][index_c];
cLH2[row1][col1]=cLH1[index_r][index_c];
cHL2[row1][col1]=cHL1[index_r][index_c];
cHH2[row1][col1]=cHH1[index_r][index_c];
col1++;
}
col1 = 0;
row1++;
}
vector<vector<double> > cLLu(len_r, vector<double>(len_c));
vector<vector<double> > cLHu(len_r, vector<double>(len_c));
vector<vector<double> > cHLu(len_r, vector<double>(len_c));
vector<vector<double> > cHHu(len_r, vector<double>(len_c));
int row_u = cLL2.size();
int col_u = cLL2[0].size();
upsamp2(cLL2,cLLu,2,2);
upsamp2(cLH2,cLHu,2,2);
upsamp2(cHL2,cHLu,2,2);
upsamp2(cHH2,cHHu,2,2);
//cLL2.clear();cLH2.clear();cHL2.clear();cHH2.clear();
vector<vector<double> > cLL00(len_r+lf, vector<double>(len_c + lf));
vector<vector<double> > cLH00(len_r+lf, vector<double>(len_c + lf));
vector<vector<double> > cHL00(len_r+lf, vector<double>(len_c + lf));
vector<vector<double> > cHH00(len_r+lf, vector<double>(len_c + lf));
per_ext2d(cLLu,cLL00,lf/2);
per_ext2d(cLHu,cLH00,lf/2);
per_ext2d(cHLu,cHL00,lf/2);
per_ext2d(cHHu,cHH00,lf/2);
//cLLu.clear();cLHu.clear();cHLu.clear();cHHu.clear();
//Shift By 1
int U = 2; // Upsampling Factor
vector<vector<double> > cLL3(len_r/2, vector<double>(len_c/2));
vector<vector<double> > cLH3(len_r/2, vector<double>(len_c/2));
vector<vector<double> > cHL3(len_r/2, vector<double>(len_c/2));
vector<vector<double> > cHH3(len_r/2, vector<double>(len_c/2));
col1 = 0;
row1 = 0;
for (int index_r = 1; index_r < len_r; index_r+=2){
for (unsigned int index_c = 1; index_c < len_c; index_c+=2){
cLL3[row1][col1]=cLL1[index_r][index_c];
cLH3[row1][col1]=cLH1[index_r][index_c];
cHL3[row1][col1]=cHL1[index_r][index_c];
cHH3[row1][col1]=cHH1[index_r][index_c];
col1++;
}
col1 = 0;
row1++;
}
vector<vector<double> > cLLu2(len_r, vector<double>(len_c));
vector<vector<double> > cLHu2(len_r, vector<double>(len_c));
vector<vector<double> > cHLu2(len_r, vector<double>(len_c));
vector<vector<double> > cHHu2(len_r, vector<double>(len_c));
row_u = cLL3.size();
col_u = cLL3[0].size();
upsamp2(cLL3,cLLu2,2,2);
upsamp2(cLH3,cLHu2,2,2);
upsamp2(cHL3,cHLu2,2,2);
upsamp2(cHH3,cHHu2,2,2);
//cLL3.clear();cLH3.clear();cHL3.clear();cHH3.clear();
cout << "STAGE 6" << endl;
vector<vector<double> > cLL01(len_r+lf, vector<double>(len_c + lf));
vector<vector<double> > cLH01(len_r+lf, vector<double>(len_c + lf));
vector<vector<double> > cHL01(len_r+lf, vector<double>(len_c + lf));
vector<vector<double> > cHH01(len_r+lf, vector<double>(len_c + lf));
per_ext2d(cLLu2,cLL01,lf/2);
per_ext2d(cLHu2,cLH01,lf/2);
per_ext2d(cHLu2,cHL01,lf/2);
per_ext2d(cHHu2,cHH01,lf/2);
cLLu2.clear();cLHu2.clear();cHLu2.clear();cHHu2.clear();
int rowsLL = cLL01.size();
int colsLL = cLL01[0].size();
vector<vector<double> > cLLt00(rowsLL + lf-1, vector<double>(colsLL));
vector<vector<double> > cLHt00(rowsLL + lf-1, vector<double>(colsLL));
vector<vector<double> > cHLt00(rowsLL + lf-1, vector<double>(colsLL));
vector<vector<double> > cHHt00(rowsLL + lf-1, vector<double>(colsLL));
vector<vector<double> > cLLt10(rowsLL + lf-1, vector<double>(colsLL));
vector<vector<double> > cLHt10(rowsLL + lf-1, vector<double>(colsLL));
vector<vector<double> > cHLt10(rowsLL + lf-1, vector<double>(colsLL));
vector<vector<double> > cHHt10(rowsLL + lf-1, vector<double>(colsLL));
vector<vector<double> > cLLt01(rowsLL + lf-1, vector<double>(colsLL + lf-1));
vector<vector<double> > cLHt01(rowsLL + lf-1, vector<double>(colsLL + lf-1));
vector<vector<double> > cHLt01(rowsLL + lf-1, vector<double>(colsLL + lf-1));
vector<vector<double> > cHHt01(rowsLL + lf-1, vector<double>(colsLL + lf-1));
vector<vector<double> > cLLt11(rowsLL + lf-1, vector<double>(colsLL + lf-1));
vector<vector<double> > cLHt11(rowsLL + lf-1, vector<double>(colsLL + lf-1));
vector<vector<double> > cHLt11(rowsLL + lf-1, vector<double>(colsLL + lf-1));
vector<vector<double> > cHHt11(rowsLL + lf-1, vector<double>(colsLL + lf-1));
vector<vector<double> > cLLt0(rowsLL + lf-1, vector<double>(colsLL + lf-1));
vector<vector<double> > cLLt1(rowsLL + lf-1, vector<double>(colsLL + lf-1));
vector<vector<double> > oupt0(len_r, vector<double>(len_c));
vector<vector<double> > oupt1(len_r, vector<double>(len_c));
vector<vector<double> > oupt(len_r, vector<double>(len_c));
for (int j=0; j< colsLL;j++) {
vector<double> sigLL0;
vector<double> sigLH0;
vector<double> sigHL0;
vector<double> sigHH0;
for (int i=0; i < rowsLL; i++) {
double temp01 = cLL00[i][j];
double temp02 = cLH00[i][j];
double temp03 = cHL00[i][j];
double temp04 = cHH00[i][j];
sigLL0.push_back(temp01);
sigLH0.push_back(temp02);
sigHL0.push_back(temp03);
sigHH0.push_back(temp04);
}
// First Convolution Step for LL,LH,HL,HH
vector<double> X0LL;
convfft(sigLL0, low_pass, X0LL);
vector<double> X0LH;
convfft(sigLH0, low_pass, X0LH);
vector<double> X0HL;
convfft(sigHL0, high_pass, X0HL);
vector<double> X0HH;
convfft(sigHH0, high_pass, X0HH);
int lent=X0LL.size();
for (int i=0; i < lent; i++) {
cLLt00[i][j]=X0LL[i];
cLHt00[i][j]=X0LH[i];
cHLt00[i][j]=X0HL[i];
cHHt00[i][j]=X0HH[i];
}
}
for (int i=0; i< rowsLL+lf-1;i++) {
vector<double> sigLL0;
vector<double> sigLH0;
vector<double> sigHL0;
vector<double> sigHH0;
for (int j=0; j < colsLL; j++) {
double temp01 = cLLt00[i][j];
double temp02 = cLHt00[i][j];
double temp03 = cHLt00[i][j];
double temp04 = cHHt00[i][j];
sigLL0.push_back(temp01);
sigLH0.push_back(temp02);
sigHL0.push_back(temp03);
sigHH0.push_back(temp04);
}
// Second Convolution Step for LL,LH,HL,HH
vector<double> X0LL;
convfft(sigLL0, low_pass, X0LL);
vector<double> X0LH;
convfft(sigLH0, high_pass, X0LH);
vector<double> X0HL;
convfft(sigHL0, low_pass, X0HL);
vector<double> X0HH;
convfft(sigHH0, high_pass, X0HH);
int lent=X0LL.size();
for (int j=0; j < lent; j++) {
cLLt01[i][j]=X0LL[j];
cLHt01[i][j]=X0LH[j];
cHLt01[i][j]=X0HL[j];
cHHt01[i][j]=X0HH[j];
cLLt0[i][j]=X0LL[j]+X0LH[j]+X0HL[j]+X0HH[j];
}
}
for (int j=0; j< colsLL;j++) {
vector<double> sigLL0;
vector<double> sigLH0;
vector<double> sigHL0;
vector<double> sigHH0;
for (int i=0; i < rowsLL; i++) {
double temp01 = cLL01[i][j];
double temp02 = cLH01[i][j];
double temp03 = cHL01[i][j];
double temp04 = cHH01[i][j];
sigLL0.push_back(temp01);
sigLH0.push_back(temp02);
sigHL0.push_back(temp03);
sigHH0.push_back(temp04);
}
// First Convolution Step for LL,LH,HL,HH
vector<double> X0LL;
convfft(sigLL0, low_pass, X0LL);
vector<double> X0LH;
convfft(sigLH0, low_pass, X0LH);
vector<double> X0HL;
convfft(sigHL0, high_pass, X0HL);
vector<double> X0HH;
convfft(sigHH0, high_pass, X0HH);
int lent=X0LL.size();
for (int i=0; i < lent; i++) {
cLLt10[i][j]=X0LL[i];
cLHt10[i][j]=X0LH[i];
cHLt10[i][j]=X0HL[i];
cHHt10[i][j]=X0HH[i];
}
}
for (int i=0; i< rowsLL + lf-1;i++) {
vector<double> sigLL0;
vector<double> sigLH0;
vector<double> sigHL0;
vector<double> sigHH0;
for (int j=0; j < colsLL; j++) {
double temp01 = cLLt10[i][j];
double temp02 = cLHt10[i][j];
double temp03 = cHLt10[i][j];
double temp04 = cHHt10[i][j];
sigLL0.push_back(temp01);
sigLH0.push_back(temp02);
sigHL0.push_back(temp03);
sigHH0.push_back(temp04);
}
// Second Convolution Step for LL,LH,HL,HH
vector<double> X0LL;
convfft(sigLL0, low_pass, X0LL);
vector<double> X0LH;
convfft(sigLH0, high_pass, X0LH);
vector<double> X0HL;
convfft(sigHL0, low_pass, X0HL);
vector<double> X0HH;
convfft(sigHH0, high_pass, X0HH);
int lent=X0LL.size();
for (int j=0; j < lent; j++) {
cLLt11[i][j]=X0LL[j];
cLHt11[i][j]=X0LH[j];
cHLt11[i][j]=X0HL[j];
cHHt11[i][j]=X0HH[j];
cLLt1[i][j]=X0LL[j]+X0LH[j]+X0HL[j]+X0HH[j];
}
}
for (int i=0; i < len_r;i++) {
for (int j=0; j < len_c;j++) {
oupt0[i][j]=cLLt0[lf+i-1][lf+j-1];
oupt1[i][j]=cLLt1[lf+i-1][lf+j-1];
}
}
circshift2d(oupt1,-1,-1);
for (int i=0; i < len_r;i++) {
for (int j=0; j < len_c;j++) {
double temp=oupt0[i][j]+oupt1[i][j];
temp=temp/2.0;
oupt[i][j]=temp;
}
}
row1 = 0;
col1 = 0;
cout << rows_n << cols_n << " " << oupt.size() << oupt[0].size() << endl;
for (int index_r = count; index_r < rows_n; index_r+=value){
for (int index_c = count; index_c < cols_n; index_c+=value){
cLL[index_r][index_c]=oupt[row1][col1];
col1++;
}
col1 = 0;
row1++;
}
cout << "STAGE 14" << endl;
}
if (iter == 1) {
sig=cLL;
}
}
return 0;
}

View File

@ -1,151 +0,0 @@
//============================================================================
// Name : wavedemo2.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : Wavelet Demo comparing linear and non-linear approximation properties
// : of a given wavelet.
//============================================================================
#include <iostream>
#include <fstream>
#include "wavelet.h"
#include <vector>
#include <string>
#include <cmath>
#include <algorithm>
using namespace std;
void findthresh(vector<double> vector1, int N, double& t){
sort(vector1.begin(), vector1.end(), greater<double>());
t = vector1.at(N-1);
}
int main() {
cout << "********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********" << endl; // prints
cout << "This program accepts signal from the user in a file format " << endl;
cout << "and performs Discrete Wavelet Transform with specified " << endl;
cout << "wavelet. " << endl;
cout << " " << endl;
cout << " The Following Wavelets are in the Database: " << endl;
cout << " haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10, " << endl;
cout << " db11, db12, db13, db14, db15. " << endl;
cout << " bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8, " << endl;
cout << " bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4," << endl;
cout << " bior5.5, bior6.8." << endl;
cout << " coif1, coif2, coif3, coif4, coif5." << endl;
cout << "Please Enter the Wavelet Name at the Prompt( No quotes) :" << endl;
string nm; // nm will store the name of Wavelet Family
cin >> nm;
cout << "Enter the name of signal file at the Prompt eg., signal.txt :" << endl;
char inp[50];
cin >> inp;
vector<double> sig;
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
exit(1);
}
while (sig_inp) {
double temp;
sig_inp >> temp;
sig.push_back(temp);
}
sig.pop_back();
vector<double> original;
original = sig;
cout << "Please Enter the Number of DWT Stages J :" << endl;
int J;
cin >> J ;
vector<double> dwt_output, flag;
// perform J-Level DWT
dwt(sig, J, nm, dwt_output,flag );
// Performing Linear Approximation by using only first 100 coefficients
// Coefficients in dwt_output are stored as following
// dwt_output =[ Appx(J-1) Detail(J-1) Detail(J-2) .... Detail(0)]
int n_coef = 100; // Number of significant coefficients
int n_non_sig= dwt_output.size() - n_coef; // Number of Coefficients that will
// be set to zero
dwt_output.erase(dwt_output.end()- n_non_sig,dwt_output.end());
// Deleting last n_non_sig coefficients and replacing them with zeros
dwt_output.insert(dwt_output.end(),n_non_sig,0);
ofstream linearsig("linsig.txt");
for (unsigned int i = 0; i < dwt_output.size(); i++) {
linearsig << dwt_output[i] << endl;
}
// Finding IDWT with approximated coefficients
vector<double> output;
idwt(dwt_output, flag,nm,output);
unsigned int count = output.size();
ofstream gnulinappx("gnulinappx.dat");
for (unsigned int i = 0;i < count; i++) {
gnulinappx << i << " " << output[i] << endl;
}
gnulinappx.close();
// Performing Non Linear Approximation by using only most
// significant coefficients
vector<double> dwt_output2, flag2;
// perform J-Level DWT
dwt(sig, J, nm, dwt_output2,flag2 );
double thresh = 0.0;
vector<double> temp_dwtoutput;
for (unsigned int i =0; i < dwt_output2.size();i++){
double temp = abs(dwt_output2[i]);
temp_dwtoutput.push_back(temp);
}
/*
for (unsigned int i =0; i < temp_dwtoutput.size(); i++){
cout << temp_dwtoutput[i] << endl;
}
*/
findthresh(temp_dwtoutput,n_coef, thresh);
for (unsigned int i = 0; i < dwt_output2.size();i++){
double temp = abs(dwt_output2[i]);
if (temp < thresh){
dwt_output2.at(i) = 0.0;
}
}
/*
for (unsigned int i =0; i < dwt_output2.size(); i++){
cout << dwt_output2[i] << endl;
}
*/
// Finding IDWT with approximated coefficients
vector<double> output2;
idwt(dwt_output2, flag2,nm,output2);
unsigned int count2 = output2.size();
cout << count2 << endl;
ofstream gnunlappx("gnunlappx.dat");
for (unsigned int i = 0;i < count2; i++) {
gnunlappx << i << " " << output2[i] << endl;
}
gnunlappx.close();
return 0;
}

View File

@ -1,83 +0,0 @@
//============================================================================
// Name : wavedemo_sym1.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : 1D DWT Demo using symmetric extension dwt_sym and idwt_sym
//============================================================================
#include <iostream>
#include <fstream>
#include "wavelet.h"
#include <vector>
#include <string>
#include <cmath>
using namespace std;
int main() {
cout << "********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********" << endl; // prints
cout << "This program accepts signal from the user in a file format " << endl;
cout << "and performs Discrete Wavelet Transform with specified " << endl;
cout << "wavelet. " << endl;
cout << " " << endl;
cout << " The Following Wavelets are in the Database: " << endl;
cout << " haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10, " << endl;
cout << " db11, db12, db13, db14, db15. " << endl;
cout << " bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8, " << endl;
cout << " bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4," << endl;
cout << " bior5.5, bior6.8." << endl;
cout << " coif1, coif2, coif3, coif4, coif5." << endl;
cout << "Please Enter the Wavelet Name at the Prompt( No quotes) :" << endl;
string nm; // nm will store the name of Wavelet Family
cin >> nm;
cout << "Enter the name of signal file at the Prompt eg., signal.txt :" << endl;
char inp[50];
cin >> inp;
vector<double> sig;
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
exit(1);
}
while (sig_inp) {
double temp;
sig_inp >> temp;
sig.push_back(temp);
}
sig.pop_back();
vector<double> original;
original = sig;
cout << "Please Enter the Number of DWT Stages J :" << endl;
int J;
cin >> J ;
vector<double> dwt_output, flag;
// perform J-Level DWT using symmetric extension. This function accepts two more
//arguments vector<int> length , a vector that stores lengths of approximation and details
// as the lengths will be different at each stage, and an integer value that corresponds
// to length of symmetric extension
vector<int> length;
int ext = 2;
dwt_sym(sig, J, nm, dwt_output,flag, length, ext );
//Perform J-Level symmetric extension IDWT
vector<double> output;
idwt_sym(dwt_output, flag,nm,output,length);
ofstream sig1("recon.txt");
ofstream diff("diff.txt");
cout <<" Recon signal size" << output.size() << endl;
for (unsigned int i = 0; i < output.size(); i++){
sig1 << output[i] << endl;
diff << output[i] - original[i] << endl;
}
gnudwtplot(J);
return 0;
}

View File

@ -1,155 +0,0 @@
//============================================================================
// Name : wavedemo_sym2.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : Wavelet Demo comparing linear and non-linear approximation properties
// : of a given wavelet. Implemented using dwt_sym and idwt_sym.
//============================================================================
#include <iostream>
#include <fstream>
#include "wavelet.h"
#include <vector>
#include <string>
#include <cmath>
#include <algorithm>
using namespace std;
void findthresh(vector<double> vector1, int N, double& t){
sort(vector1.begin(), vector1.end(), greater<double>());
t = vector1.at(N-1);
}
int main() {
cout << "********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********" << endl; // prints
cout << "This program accepts signal from the user in a file format " << endl;
cout << "and performs Discrete Wavelet Transform with specified " << endl;
cout << "wavelet. " << endl;
cout << " " << endl;
cout << " The Following Wavelets are in the Database: " << endl;
cout << " haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10, " << endl;
cout << " db11, db12, db13, db14, db15. " << endl;
cout << " bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8, " << endl;
cout << " bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4," << endl;
cout << " bior5.5, bior6.8." << endl;
cout << " coif1, coif2, coif3, coif4, coif5." << endl;
cout << "Please Enter the Wavelet Name at the Prompt( No quotes) :" << endl;
string nm; // nm will store the name of Wavelet Family
cin >> nm;
cout << "Enter the name of signal file at the Prompt eg., signal.txt :" << endl;
char inp[50];
cin >> inp;
vector<double> sig;
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
exit(1);
}
while (sig_inp) {
double temp;
sig_inp >> temp;
sig.push_back(temp);
}
sig.pop_back();
vector<double> original;
original = sig;
cout << "Please Enter the Number of DWT Stages J :" << endl;
int J;
cin >> J ;
vector<double> dwt_output, flag;
vector<int> length1;
int ext = 2;
// perform J-Level DWT
dwt_sym(sig, J, nm, dwt_output,flag, length1,ext );
// Performing Linear Approximation by using only first 100 coefficients
// Coefficients in dwt_output are stored as following
// dwt_output =[ Appx(J-1) Detail(J-1) Detail(J-2) .... Detail(0)]
int n_coef = 100; // Number of significant coefficients
int n_non_sig= dwt_output.size() - n_coef; // Number of Coefficients that will
// be set to zero
dwt_output.erase(dwt_output.end()- n_non_sig,dwt_output.end());
// Deleting last n_non_sig coefficients and replacing them with zeros
dwt_output.insert(dwt_output.end(),n_non_sig,0);
ofstream linearsig("linsig.txt");
for (unsigned int i = 0; i < dwt_output.size(); i++) {
linearsig << dwt_output[i] << endl;
}
// Finding IDWT with approximated coefficients
vector<double> output;
idwt_sym(dwt_output, flag,nm,output, length1);
unsigned int count = output.size();
ofstream gnulinappx("gnulinappx.dat");
for (unsigned int i = 0;i < count; i++) {
gnulinappx << i << " " << output[i] << endl;
}
gnulinappx.close();
// Performing Non Linear Approximation by using only most
// significant coefficients
vector<double> dwt_output2, flag2;
vector<int> length2;
// perform J-Level DWT
dwt_sym(sig, J, nm, dwt_output2,flag2,length2, ext );
double thresh = 0.0;
vector<double> temp_dwtoutput;
for (unsigned int i =0; i < dwt_output2.size();i++){
double temp = abs(dwt_output2[i]);
temp_dwtoutput.push_back(temp);
}
/*
for (unsigned int i =0; i < temp_dwtoutput.size(); i++){
cout << temp_dwtoutput[i] << endl;
}
*/
findthresh(temp_dwtoutput,n_coef, thresh);
for (unsigned int i = 0; i < dwt_output2.size();i++){
double temp = abs(dwt_output2[i]);
if (temp < thresh){
dwt_output2.at(i) = 0.0;
}
}
/*
for (unsigned int i =0; i < dwt_output2.size(); i++){
cout << dwt_output2[i] << endl;
}
*/
// Finding IDWT with approximated coefficients
vector<double> output2;
idwt_sym(dwt_output2, flag2,nm,output2, length2);
unsigned int count2 = output2.size();
cout << count2 << endl;
ofstream gnunlappx("gnunlappx.dat");
for (unsigned int i = 0;i < count2; i++) {
gnunlappx << i << " " << output2[i] << endl;
}
gnunlappx.close();
return 0;
}

45
front.md Normal file
View File

@ -0,0 +1,45 @@
# C++ 1D/2D DWT Implementation for Win32 and Linux #
### Wavelet2d Libraries ###
1. 1D DWT and IDWT Implementation (Two Modes)
1. 2D DWT and IDWT Implementation (Two Modes)
1. 1D SWT and ISWT Implementation ( Stationary Wavelet Transform)
1. 2D SWT Implementation
1. Implemented using FFTW3 Library
1. Shared(.so) and static(.a) libraries for Linux
1. Shared(.dll) and static(.a) libraries for Win32 GCC (MinGW).
1. Shared(.dll) libraries for Microsoft VC++
> This implementation uses C++ vector objects to accept input, store and output data. This is done to overcome certain programming limitations associated with using arrays. Dynamic arrays were also an option but they require a lot of house-cleaning without having any advantages over vector objects. To learn more about vectors, please refer to excellent tutorial at [CPLUSPLUS](http://www.cplusplus.com/reference/stl/vector/). Vectors and Arrays can be converted back and forth so even if you are more comfortable with arrays, using vectors should not really be a problem.
### Changes from Previous Version ###
Focus is on speed.
1. FFTW3 Library is used to improve computation speed.
2. No GNUPLOT outputs are generated.
3. Periodic and Symmetric functions take same arguments. They will still be accessed by the same names, though.(dwt ,dwt\_sym etc.)
4. Focus on shared libraries. No static libraries for MSVC++ although MinGW and LINUX version will come with static as well as shared libraries.
wavelet2d - dynamic libraries( .so and .dll)
wavelet2s - static libraries (.a)
|**[List of Functions](http://code.google.com/p/wavelet1d/wiki/newfunc)**| Lists all Functions available in the Library|
|:-----------------------------------------------------------------------|:--------------------------------------------|
|**[Example Code 1](http://code.google.com/p/wavelet1d/wiki/new1DDWTdemo)**| 1D DWT/IDWT Demo Code|
|**[Example Code 2](http://code.google.com/p/wavelet1d/wiki/new1DAppx)**| 1D Signal Approximation Demo|
|**[Example Code 3](http://code.google.com/p/wavelet1d/wiki/new2DDWTdemo)**| 2D DWT/IDWT Demo Code|
|**[Example Code 4](http://code.google.com/p/wavelet1d/wiki/new2DAppx)**| Image Approximation Demo|
|**[Example Code 5](http://code.google.com/p/wavelet1d/wiki/new2DSWTdemo)**| 2D SWT Demo|
|**[Example Code 6](http://code.google.com/p/wavelet1d/wiki/new1DSWTDemo)**| 1D SWT Demo Code|
![https://lh4.googleusercontent.com/-4w-fWQyoieo/Thn_s7qb8-I/AAAAAAAAAGs/B0HFvLru6CU/s512/empire.jpg](https://lh4.googleusercontent.com/-4w-fWQyoieo/Thn_s7qb8-I/AAAAAAAAAGs/B0HFvLru6CU/s512/empire.jpg)
_J=2 Level Discrete Wavelet Transform of a 569X800 image using dwt\_2d\_sym function (Resized here for Display)_
Image Processing Note : I have not implemented any image class in C++ so I'm using OPENCV to handle images. It happens to be a rather bulky package and if you are not already working in image processing area, there are other more convenient options that may be used to handle simple image operations( loading, displaying, saving and converting them to c++ STL formats).

93
install.md Normal file
View File

@ -0,0 +1,93 @@
# Working with Wavelet Libraries #
## Wavelet Libraries in Win32 Environment ##
### Microsoft Visual C++ ###
This package contains two DLLs for MSVC++ - one Debug and one Release
version.The list of required files in order to compile wavelet2d based programs-
#Header File- wavelet2d.h
#Import Library- wavelet2d.lib
#Wavelet DLL - wavelet2d.dll
#FFTW DLL - libfftw3-3.dll
Header file is in the source (src) folder. Wavelet Libraries are in the respective Debug and Release folders. FFTW DLL is in the FFTW3 folder. Alternatively, you may chose to install FFT library from www.fftw.org. The FFTW sourcecodes are also available at FFTW website under GNU-GPL license.
In order to use wavelet libraries, the easiest way is to add import library
(wavelet2d.lib) to additional dependency in your project which in turn will
handle the DLLs for you. The two DLLs must be in your program path.If you
are new to MSVC, you may want to learn more about DLL search path at
[DLL Search Path](http://msdn.microsoft.com/en-us/library/7d83bc18(VS.71).aspx)
You may also chose to directly call DLLs from your program.Regardless
of how you handle DLLs, mixing debug and release versions is not a good
idea.Both versions are named wavelet2d.dll so putting them in system path is
not a good idea either. Preferred way is to use Visual Studio project settings
to link to the wavelet2d.lib file and put the release and debug wavelet2d dlls
along with libfftw-3.3dll in the directory containing the respective release and
debug executables of your project. Import library will open the DLLs.
### GNU-GCC (MinGW) Based Compilation ###
If you use GCC compiler either through MSYS or from one of the IDEs(Codeblocks,
Eclipse, QTcreator, Netbeans etc.),I have also added both debug and release
versions of wavelet2d DLLs and wavelet2s static libraries. Required Files for
MinGW DLLS-
• Header Files- wavelet2d.h
• Import Library- libwavelet2d.dll.a
• Wavelet DLL - wavelet2d.dll
• FFTW DLL - libfftw3-3.dll (Import library is also included)
It is recommended that you link to the Release and Debug folders as they are.
Once you link to import library and specify the folder location, wavelet import
library should automatically open the two DLLs. Mixing Debug and Release
versions shouldnt pose any problems in this case.
Working with MinGW Static libraries is even more straightforward. You
need to include wavelet2s.h header in your program , link to static .a library and you are set.
**Known Issue - Some newer versions of MinGW-g++ compiler have problem
working with .o codes(and hence static libraries) compiled in older versions of MinGW (3.x). If you are facing this problem try MINGW4.5 compiled static libraries or build wavelet2d from the source code with your own compiler. You'll need to statically build fftw3 library first if you are going the source code way. The DLLs should be working fine in any case so that's always another option.**
## Working in LINUX Environment ##
1. This package contains two wavelet libraries- libwavelet2d.so.1.0 (shared)
and libwavelet2s.a (static) compiled essentially from the same source code.
Source code is available in the src folder.
2. You may need to link to header files that are included with their respective libraries. They are also available in the src folder.
3. You may want to install shared library in one of your existing paths to
make compilation easier. You can create sym links once inside the folder(
eg., /usr/local/lib where you are installing libwavelet2d.so.1.0) by using following commands
> ln -sf libwavelet2d.so.1.0 libwavelet2d.so
> ln -sf libwavelet2d.so.1.0 libwavelet2d.so.1
> ldconfig
You will probably need superuser privileges to perform previous steps. If you
dont have su privilege then you can move libwavelet2d.so.1.0 to your work
folder or where your source code is, create sym links as before and then put
your folder in the path during runtime.
ln -sf libwavelet2d.so.1.0 libwavelet2d.so
ln -sf libwavelet2d.so.1.0 libwavelet2d.so.1
export LD\_LIBRARY\_PATH=.
libwavelet2s.a :: Working with static library is pretty straightforward. You will
only need to include wavelet2s.h in your program and specify the library
(-lwavelet2s flag) , include path (-I<path to wavelet2s.h> flag) and library
path (-L<path to libwavelet2s.a> flag).

View File

@ -1,3 +1,14 @@
# 1D Linear vs Nonlinear Approximation #
_Note_
1. dwt and dwt\_sym functions are interchangeable in the following code as they take the same arguments. You may have to make some trivial modifications due to different sized output coeffficients.
2. Please make sure that right header file is included. Following sample program links to wavelet2s.h which is the header for static libraries. wavelet2d.h must be included for shared libraries.
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/wavelet2d/demo/wavedemo2.cpp)
```
//============================================================================
// Name : wavedemo2.cpp
// Author : Rafat Hussain
@ -159,3 +170,28 @@ int main() {
return 0;
}
```
This program computes DWT of the 256-point signal and then uses only 100 coefficients to reconstruct the signal. In the first case, first 100 coefficients are are used to compute linear approximation. In the second case, 100 largest coefficients are used by calculating a threshold that separates largest 100 coefficients from the others.The wavelet used is db3 and the signal is decomposed and reconstructed over 5 stages of DWT/IDWT. The results are plotted below.
![https://lh3.googleusercontent.com/-786mdxcFiFw/Tk-HwRh25GI/AAAAAAAAAMM/rE5xc6ngnv0/s800/1dappxscreen.png](https://lh3.googleusercontent.com/-786mdxcFiFw/Tk-HwRh25GI/AAAAAAAAAMM/rE5xc6ngnv0/s800/1dappxscreen.png)
_Console showing db3 5 level computation_
![https://lh5.googleusercontent.com/-wAxR0xM5I38/Tk9_iWhol_I/AAAAAAAAAL4/C9Sck_VZ7Ms/s912/1ddwtsig.png](https://lh5.googleusercontent.com/-wAxR0xM5I38/Tk9_iWhol_I/AAAAAAAAAL4/C9Sck_VZ7Ms/s912/1ddwtsig.png)
_Length 256 Piecewise Regular signal from WaveLab_
In Linear Approximation case, only first 100 coefficients are retained. Others are set to zero.
![https://lh3.googleusercontent.com/-WIIVJSzPjJI/Tk-HwGSTXxI/AAAAAAAAAMI/kzHzVRuIqeY/s912/linsigcoeff.png](https://lh3.googleusercontent.com/-WIIVJSzPjJI/Tk-HwGSTXxI/AAAAAAAAAMI/kzHzVRuIqeY/s912/linsigcoeff.png)
_Retained Coefficients for Linear Approximation case_
![https://lh5.googleusercontent.com/-vo62gHChC0U/Tk-HvyiCgyI/AAAAAAAAAMA/NrpX9FBIOXU/s912/1dlinappx.png](https://lh5.googleusercontent.com/-vo62gHChC0U/Tk-HvyiCgyI/AAAAAAAAAMA/NrpX9FBIOXU/s912/1dlinappx.png)
_Reconstructed Signal using Linear Approximation_
In Non-Linear case, largest 100 coefficients are retained.
![https://lh3.googleusercontent.com/-2hvwAm8QTyU/Tk-HvuIZwjI/AAAAAAAAAL8/LxS0wb_IFOk/s912/nonlinsigcoeff.png](https://lh3.googleusercontent.com/-2hvwAm8QTyU/Tk-HvuIZwjI/AAAAAAAAAL8/LxS0wb_IFOk/s912/nonlinsigcoeff.png)
_Retained Coefficients(Non-Linear Approximation case_
![https://lh4.googleusercontent.com/-OCLIjzcaO7U/Tk-Hv2ClRaI/AAAAAAAAAME/C-0CzXX8moI/s912/1dnlappx.png](https://lh4.googleusercontent.com/-OCLIjzcaO7U/Tk-Hv2ClRaI/AAAAAAAAAME/C-0CzXX8moI/s912/1dnlappx.png)
_Reconstructed Signal(Non-Linear Approximation Case)_

View File

@ -1,14 +1,26 @@
# 1D DWT/IDWT Demo using dwt function #
_Notes_
1. dwt and dwt\_sym functions are interchangeable in the following code as they take the same arguments.
2. Please make sure that right header file is included. Following sample program links to wavelet2d.h which is the header for shared libraries. wavelet2s.h must be included for static libraries.
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/wavelet2d/demo/wavedemo1.cpp)
```
//============================================================================
// Name : wavedemo1.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Copyright :
// Description : 1D DWT Demo
//============================================================================
#include <iostream>
#include <fstream>
#include "wavelet.h"
#include "wavelet2d.h"
#include <vector>
#include <string>
#include <cmath>
@ -38,7 +50,6 @@ int main() {
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
exit(1);
}
while (sig_inp) {
double temp;
@ -56,12 +67,19 @@ int main() {
vector<double> dwt_output, flag;
// perform J-Level DWT
dwt(sig, J, nm, dwt_output,flag );
vector<int> length;
dwt_sym(sig, J, nm, dwt_output,flag,length);
ofstream dwtout("dwtout.txt");
for (unsigned int i = 0; i < dwt_output.size(); i++){
dwtout << dwt_output[i] << endl;
}
//Perform J-Level IDWT
vector<double> output;
idwt(dwt_output, flag,nm,output);
idwt_sym(dwt_output, flag,nm,output,length);
ofstream sig1("recon.txt");
ofstream diff("diff.txt");
@ -72,6 +90,22 @@ int main() {
diff << output[i] - original[i] << endl;
}
gnudwtplot(J);
//gnudwtplot(J);
return 0;
}
```
This sample program asks user for wavelet name, signal file and number of DWT stages. It then computes DWT of the input signal and then the IDWT from the wavelet coefficients so obtained.
![https://lh3.googleusercontent.com/-wIrGfF_x4ug/Tk9_idI6YiI/AAAAAAAAAL0/jIFwli0Tndk/s912/1ddwtscreen.png](https://lh3.googleusercontent.com/-wIrGfF_x4ug/Tk9_idI6YiI/AAAAAAAAAL0/jIFwli0Tndk/s912/1ddwtscreen.png)
As can be seen, outputs are in _.txt_ format but they can be modified and plotted with any software of your choice.
![https://lh5.googleusercontent.com/-wAxR0xM5I38/Tk9_iWhol_I/AAAAAAAAAL4/C9Sck_VZ7Ms/s912/1ddwtsig.png](https://lh5.googleusercontent.com/-wAxR0xM5I38/Tk9_iWhol_I/AAAAAAAAAL4/C9Sck_VZ7Ms/s912/1ddwtsig.png)
_Length 256 Piecewise Regular signal from WaveLab_
![https://lh4.googleusercontent.com/-xG9LotALuPs/Tk9_iFkYsiI/AAAAAAAAALw/G0S0ipsAOKI/s912/1ddwtout.png](https://lh4.googleusercontent.com/-xG9LotALuPs/Tk9_iFkYsiI/AAAAAAAAALw/G0S0ipsAOKI/s912/1ddwtout.png)
_2 Level DWT Decomposition Coefficients obtained using db2 wavelet_
![https://lh6.googleusercontent.com/-DscYhVPOEPY/Tk9_iFvaZTI/AAAAAAAAALs/3q4hfboBLLA/s912/1ddwtrecon.png](https://lh6.googleusercontent.com/-DscYhVPOEPY/Tk9_iFvaZTI/AAAAAAAAALs/3q4hfboBLLA/s912/1ddwtrecon.png)
_Reconstructed Signal After IDWT computations_

View File

@ -1,3 +1,15 @@
# 1D Stationary Wavelet Transform Demo #
Notes
1. dwt and dwt\_sym functions are interchangeable in the following code as they take the same arguments.
2. Please make sure that right header file is included. Following sample program links to wavelet2d.h which is the header for shared libraries. wavelet2s.h must be included for static libraries.
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/wavelet2d/demo/swtdemo.cpp)
```
//============================================================================
// Name : swtdemo.cpp
// Author : Rafat Hussain
@ -83,3 +95,17 @@ int main() {
return 0;
}
```
![https://lh4.googleusercontent.com/-f2xNxK3vGHo/Tk-QtuCS_7I/AAAAAAAAAMY/LvvYQpISVIo/s912/swt1dscreen.png](https://lh4.googleusercontent.com/-f2xNxK3vGHo/Tk-QtuCS_7I/AAAAAAAAAMY/LvvYQpISVIo/s912/swt1dscreen.png)
_Console Running swt demo_
![https://lh5.googleusercontent.com/-wAxR0xM5I38/Tk9_iWhol_I/AAAAAAAAAL4/C9Sck_VZ7Ms/s912/1ddwtsig.png](https://lh5.googleusercontent.com/-wAxR0xM5I38/Tk9_iWhol_I/AAAAAAAAAL4/C9Sck_VZ7Ms/s912/1ddwtsig.png)
_Input Signal(Length-256)_
![https://lh3.googleusercontent.com/-mIua34Jqmkg/Tk-QtY0G5yI/AAAAAAAAAMU/2p14kFkXlzI/s912/swtcoeff.png](https://lh3.googleusercontent.com/-mIua34Jqmkg/Tk-QtY0G5yI/AAAAAAAAAMU/2p14kFkXlzI/s912/swtcoeff.png)
_SWT Coefficients for two level of Decomposition(Length 3 X 256)_
![https://lh5.googleusercontent.com/-ZkYxAhK7oyE/Tk-QtesE_1I/AAAAAAAAAMQ/rxp5uyVtMQg/s912/swtrecon.png](https://lh5.googleusercontent.com/-ZkYxAhK7oyE/Tk-QtesE_1I/AAAAAAAAAMQ/rxp5uyVtMQg/s912/swtrecon.png)
_Reconstructed Signal_

View File

@ -1,341 +1,361 @@
//============================================================================
// Name : imagedemo2.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : Image Approximation using symmetric or periodic extension 2D DWT
//============================================================================
// IMPORTANT - Algorithm used to display Image is imprecise because of int 8 overflow issues
// and it shouldn't be used to judge the performance of the DWT. The DWT and IDWT outputs
// should be used for performance measurements. I have used maximum value rescaling to
// solve overflow issues and , obviously, it is going to result in suboptimal performance but
// it is good enough for demonstration purposes.
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <complex>
#include <cmath>
#include <algorithm>
#include "wavelet2s.h"
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
using namespace std;
using namespace cv;
void findthresh(vector<double> &vector1, int N, double& t){
sort(vector1.begin(), vector1.end(), greater<double>());
t = vector1.at(N-1);
}
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
void* maxval1(vector<double> &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
if (max <= arr[i]){
max = arr[i];
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("lena512.bmp");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
cvSaveImage("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
string nm = "db2";
vector<double> l1,h1,l2,h2;
filtcoef(nm,l1,h1,l2,h2);
// unsigned int lf=l1.size();
// int rows_n =(int) (rows+ J*(lf-1));
// int cols_n =(int) (cols + J * ( lf -1));
// Finding 2D DWT Transform of the image using symetric extension algorithm
// Extension is set to 0 (eg., int e = 0)
vector<int> length;
vector<double> output,flag;
int J =6;
dwt_2d(vec1,J,nm,output,flag,length);
double max;
vector<int> length2;
// This algorithm computes DWT of image of any given size. Together with convolution and
// subsampling operations it is clear that subsampled images are of different length than
// dyadic length images. In order to compute the "effective" size of DWT we do additional
// calculations.
dwt_output_dim_sym(length,length2,J);
// length2 is gives the integer vector that contains the size of subimages that will
// combine to form the displayed output image. The last two entries of length2 gives the
// size of DWT ( rows_n by cols_n)
int siz = length2.size();
int rows_n=length2[siz-2];
int cols_n = length2[siz-1];
vector<vector< double> > dwtdisp(rows_n, vector<double>(cols_n));
dispDWT(output,dwtdisp, length ,length2, J);
// dispDWT returns the 2D object dwtdisp which will be displayed using OPENCV's image
// handling functions
vector<vector<double> > dwt_output= dwtdisp;
// Storing the DWT coefficients in two different vectors that will be used to approximate
// Image with two different sets of chosen coefficients.
vector<double> dwt_coef1;
vector<double> dwt_coef2;
dwt_coef1 = output;
dwt_coef2 = output;
maxval(dwt_output,max);// max value is needed to take care of overflow which happens because
// of convolution operations performed on unsigned 8 bit images
//Displaying Scaled Image
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = cols_n;
imgSize.height = rows_n;
cvImg = cvCreateImage( imgSize, 8, 1 );
// dwt_hold is created to hold the dwt output as further operations need to be
// carried out on dwt_output in order to display scaled images.
vector<vector<double> > dwt_hold(rows_n, vector<double>( cols_n));
dwt_hold = dwt_output;
// Setting coefficients of created image to the scaled DWT output values
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( dwt_output[i][j] <= 0.0){
dwt_output[i][j] = 0.0;
}
if ( i <= (length2[0]) && j <= (length2[1]) ) {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (dwt_output[i][j] / max) * 255.0);
} else {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) (dwt_output[i][j]) ;
}
}
}
cvNamedWindow( "DWT Image", 1 ); // creation of a visualisation window
cvShowImage( "DWT Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("DWT Image");
cvSaveImage("dwt.bmp",cvImg);
// Case 1 : Only 10% of the largest coefficients are considered
// Output is the 1D DWT vector
int n_coef1= int (output.size()/ 10);
cout << n_coef1 << endl;
// Finding Threshold Value corresponding to n_coef1
vector<double> temp1;
cout << "size: " << (int) temp1.size() << "\n";
cout << "capacity: " << (int) temp1.capacity() << "\n";
cout << "max_size: " << (int) temp1.max_size() << "\n";
for (unsigned int i =0; i < dwt_coef1.size(); i++) {
double tempval = abs(dwt_coef1[i]);
temp1.push_back(tempval);
}
double thresh1= 0.0;
findthresh(temp1,n_coef1,thresh1);
cout << "thresh" << thresh1 << endl;
ofstream temp("temp.txt");
for (unsigned int i =0; i < temp1.size(); i++){
temp << temp1[i] << " " ;
}
// Reset coeffficients value depending on threshold value
for (unsigned int i =0; i < dwt_coef1.size(); i++) {
double temp = abs(dwt_coef1[i]);
if (temp < thresh1){
dwt_coef1.at(i)= 0.0;
}
}
// Finding IDWT
vector<vector<double> > idwt_output(rows, vector<double>(cols));
idwt_2d( dwt_coef1,flag, nm, idwt_output,length);
double max1;
maxval(idwt_output,max1);
//Displaying Reconstructed Image
IplImage *dvImg;
CvSize dvSize; // size of output image
dvSize.width = idwt_output[0].size();
dvSize.height = idwt_output.size();
cout << idwt_output.size() << idwt_output[0].size() << endl;
dvImg = cvCreateImage( dvSize, 8, 1 );
for (int i = 0; i < dvSize.height; i++ ){
for (int j = 0; j < dvSize.width; j++ ){
if ( idwt_output[i][j] <= 0.0){
idwt_output[i][j] = 0.0;
}
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) ((idwt_output[i][j] / max1) * 255 ) ;
}
}
cvNamedWindow( "10% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "10% Coeff Reconstructed Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("10% Coeff Reconstructed Image");
cvSaveImage("recon.bmp",dvImg);
// Case 2 : Only 2% of the largest coefficients are considered
// Output is the 1D DWT vector
int n_coef2= int (output.size()/ 50);
cout << n_coef2 << endl;
// Finding Threshold Value corresponding to n_coef1
vector<double> temp2;
for (unsigned int i =0; i < dwt_coef2.size(); i++) {
double tempval = abs(dwt_coef2[i]);
temp2.push_back(tempval);
}
double thresh2= 0.0;
findthresh(temp2,n_coef2,thresh2);
cout << "thresh" << thresh2 << endl;
// Reset coeffficients value depending on threshold value
for (unsigned int i =0; i < dwt_coef2.size(); i++) {
double temp = abs(dwt_coef2[i]);
if (temp < thresh2){
dwt_coef2.at(i)= 0.0;
}
}
// Finding IDWT
vector<vector<double> > idwt_output2(rows, vector<double>(cols));
idwt_2d( dwt_coef2,flag, nm, idwt_output2,length);
double max2;
maxval(idwt_output2,max2);
//Displaying Reconstructed Image
IplImage *dvImg2;
CvSize dvSize2; // size of output image
dvSize2.width = idwt_output2[0].size();
dvSize2.height = idwt_output2.size();
cout << idwt_output2.size() << idwt_output2[0].size() << endl;
dvImg2 = cvCreateImage( dvSize2, 8, 1 );
for (int i = 0; i < dvSize2.height; i++ ) {
for (int j = 0; j < dvSize2.width; j++ ) {
if ( idwt_output2[i][j] <= 0.0){
idwt_output2[i][j] = 0.0;
}
((uchar*)(dvImg2->imageData + dvImg2->widthStep*i))[j] =
(char) ((idwt_output2[i][j]/ max2) * 255 ) ;
}
}
cvNamedWindow( "2% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "2% Coeff Reconstructed Image", dvImg2 ); // image visualisation
cvWaitKey();
cvDestroyWindow("2% Coeff Reconstructed Image");
cvSaveImage("recon2.bmp",dvImg2);
return 0;
}
# Image Approximation #
_Note_
1. dwt\_2d and dwt\_2d\_sym functions are interchangeable in the following code as they take the same arguments. You may have to make some trivial modifications due to different sized output coeffficients.
2. Please make sure that right header file is included. Following sample program links to wavelet2s.h which is the header for static libraries. wavelet2d.h must be included for shared libraries.
3. I'm using [OPENCV](http://opencv.willowgarage.com/wiki/) to handle images as i already use OPENCV for other image processing work. You may want to use some simpler image libraries as OPENCV is a full image processing suite and is very bulky or you can just use 2D matrices/build your own image classes. Regardless, DWT/IDWT operations are more important than the choice of libraries.
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/wavelet2d/demo/imagedemo2.cpp)
```
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <complex>
#include <cmath>
#include <algorithm>
#include "wavelet2s.h"
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
using namespace std;
using namespace cv;
void findthresh(vector<double> &vector1, int N, double& t){
sort(vector1.begin(), vector1.end(), greater<double>());
t = vector1.at(N-1);
}
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
void* maxval1(vector<double> &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
if (max <= arr[i]){
max = arr[i];
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("lena512.bmp");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
cvSaveImage("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
string nm = "db2";
vector<double> l1,h1,l2,h2;
filtcoef(nm,l1,h1,l2,h2);
// unsigned int lf=l1.size();
// int rows_n =(int) (rows+ J*(lf-1));
// int cols_n =(int) (cols + J * ( lf -1));
// Finding 2D DWT Transform of the image using symetric extension algorithm
// Extension is set to 0 (eg., int e = 0)
vector<int> length;
vector<double> output,flag;
int J =6;
dwt_2d(vec1,J,nm,output,flag,length);
double max;
vector<int> length2;
// This algorithm computes DWT of image of any given size. Together with convolution and
// subsampling operations it is clear that subsampled images are of different length than
// dyadic length images. In order to compute the "effective" size of DWT we do additional
// calculations.
dwt_output_dim_sym(length,length2,J);
// length2 is gives the integer vector that contains the size of subimages that will
// combine to form the displayed output image. The last two entries of length2 gives the
// size of DWT ( rows_n by cols_n)
int siz = length2.size();
int rows_n=length2[siz-2];
int cols_n = length2[siz-1];
vector<vector< double> > dwtdisp(rows_n, vector<double>(cols_n));
dispDWT(output,dwtdisp, length ,length2, J);
// dispDWT returns the 2D object dwtdisp which will be displayed using OPENCV's image
// handling functions
vector<vector<double> > dwt_output= dwtdisp;
// Storing the DWT coefficients in two different vectors that will be used to approximate
// Image with two different sets of chosen coefficients.
vector<double> dwt_coef1;
vector<double> dwt_coef2;
dwt_coef1 = output;
dwt_coef2 = output;
maxval(dwt_output,max);// max value is needed to take care of overflow which happens because
// of convolution operations performed on unsigned 8 bit images
//Displaying Scaled Image
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = cols_n;
imgSize.height = rows_n;
cvImg = cvCreateImage( imgSize, 8, 1 );
// dwt_hold is created to hold the dwt output as further operations need to be
// carried out on dwt_output in order to display scaled images.
vector<vector<double> > dwt_hold(rows_n, vector<double>( cols_n));
dwt_hold = dwt_output;
// Setting coefficients of created image to the scaled DWT output values
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( dwt_output[i][j] <= 0.0){
dwt_output[i][j] = 0.0;
}
if ( i <= (length2[0]) && j <= (length2[1]) ) {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (dwt_output[i][j] / max) * 255.0);
} else {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) (dwt_output[i][j]) ;
}
}
}
cvNamedWindow( "DWT Image", 1 ); // creation of a visualisation window
cvShowImage( "DWT Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("DWT Image");
cvSaveImage("dwt.bmp",cvImg);
// Case 1 : Only 10% of the largest coefficients are considered
// Output is the 1D DWT vector
int n_coef1= int (output.size()/ 10);
cout << n_coef1 << endl;
// Finding Threshold Value corresponding to n_coef1
vector<double> temp1;
cout << "size: " << (int) temp1.size() << "\n";
cout << "capacity: " << (int) temp1.capacity() << "\n";
cout << "max_size: " << (int) temp1.max_size() << "\n";
for (unsigned int i =0; i < dwt_coef1.size(); i++) {
double tempval = abs(dwt_coef1[i]);
temp1.push_back(tempval);
}
double thresh1= 0.0;
findthresh(temp1,n_coef1,thresh1);
cout << "thresh" << thresh1 << endl;
ofstream temp("temp.txt");
for (unsigned int i =0; i < temp1.size(); i++){
temp << temp1[i] << " " ;
}
// Reset coeffficients value depending on threshold value
for (unsigned int i =0; i < dwt_coef1.size(); i++) {
double temp = abs(dwt_coef1[i]);
if (temp < thresh1){
dwt_coef1.at(i)= 0.0;
}
}
// Finding IDWT
vector<vector<double> > idwt_output(rows, vector<double>(cols));
idwt_2d( dwt_coef1,flag, nm, idwt_output,length);
double max1;
maxval(idwt_output,max1);
//Displaying Reconstructed Image
IplImage *dvImg;
CvSize dvSize; // size of output image
dvSize.width = idwt_output[0].size();
dvSize.height = idwt_output.size();
cout << idwt_output.size() << idwt_output[0].size() << endl;
dvImg = cvCreateImage( dvSize, 8, 1 );
for (int i = 0; i < dvSize.height; i++ ){
for (int j = 0; j < dvSize.width; j++ ){
if ( idwt_output[i][j] <= 0.0){
idwt_output[i][j] = 0.0;
}
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) ((idwt_output[i][j] / max1) * 255 ) ;
}
}
cvNamedWindow( "10% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "10% Coeff Reconstructed Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("10% Coeff Reconstructed Image");
cvSaveImage("recon.bmp",dvImg);
// Case 2 : Only 2% of the largest coefficients are considered
// Output is the 1D DWT vector
int n_coef2= int (output.size()/ 50);
cout << n_coef2 << endl;
// Finding Threshold Value corresponding to n_coef1
vector<double> temp2;
for (unsigned int i =0; i < dwt_coef2.size(); i++) {
double tempval = abs(dwt_coef2[i]);
temp2.push_back(tempval);
}
double thresh2= 0.0;
findthresh(temp2,n_coef2,thresh2);
cout << "thresh" << thresh2 << endl;
// Reset coeffficients value depending on threshold value
for (unsigned int i =0; i < dwt_coef2.size(); i++) {
double temp = abs(dwt_coef2[i]);
if (temp < thresh2){
dwt_coef2.at(i)= 0.0;
}
}
// Finding IDWT
vector<vector<double> > idwt_output2(rows, vector<double>(cols));
idwt_2d( dwt_coef2,flag, nm, idwt_output2,length);
double max2;
maxval(idwt_output2,max2);
//Displaying Reconstructed Image
IplImage *dvImg2;
CvSize dvSize2; // size of output image
dvSize2.width = idwt_output2[0].size();
dvSize2.height = idwt_output2.size();
cout << idwt_output2.size() << idwt_output2[0].size() << endl;
dvImg2 = cvCreateImage( dvSize2, 8, 1 );
for (int i = 0; i < dvSize2.height; i++ ) {
for (int j = 0; j < dvSize2.width; j++ ) {
if ( idwt_output2[i][j] <= 0.0){
idwt_output2[i][j] = 0.0;
}
((uchar*)(dvImg2->imageData + dvImg2->widthStep*i))[j] =
(char) ((idwt_output2[i][j]/ max2) * 255 ) ;
}
}
cvNamedWindow( "2% Coeff Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "2% Coeff Reconstructed Image", dvImg2 ); // image visualisation
cvWaitKey();
cvDestroyWindow("2% Coeff Reconstructed Image");
cvSaveImage("recon2.bmp",dvImg2);
return 0;
}
```
This code decomposes a 512X512 grayscale image to 6 levels using db2 wavelets and uses a) only 10% coefficients and b) only 2% coefficients to reconstruct the image.
Input Image
![https://lh5.googleusercontent.com/-Y78s7sxlRcM/TlAItad_y4I/AAAAAAAAANM/fKDn4Um6Awo/lena512.jpg](https://lh5.googleusercontent.com/-Y78s7sxlRcM/TlAItad_y4I/AAAAAAAAANM/fKDn4Um6Awo/lena512.jpg)
DWT of Input Image
![https://lh6.googleusercontent.com/-un5jMZe5jWE/TlAIuMAx6cI/AAAAAAAAANQ/om0EtqX-mck/2dappxdwt.jpg](https://lh6.googleusercontent.com/-un5jMZe5jWE/TlAIuMAx6cI/AAAAAAAAANQ/om0EtqX-mck/2dappxdwt.jpg)
Image Approximation using only 10% coefficients
![https://lh6.googleusercontent.com/-wkhbPVWQk0g/TlAIsFBBL9I/AAAAAAAAANI/2BkdWP2mcgs/2dappxrecon.jpg](https://lh6.googleusercontent.com/-wkhbPVWQk0g/TlAIsFBBL9I/AAAAAAAAANI/2BkdWP2mcgs/2dappxrecon.jpg)
Image Approximation using only 2% coefficients.
![https://lh4.googleusercontent.com/-LyvXNI1CUGE/TlAIw0icqgI/AAAAAAAAANY/0PIQ6Gz5HDQ/2dappxrecon2.jpg](https://lh4.googleusercontent.com/-LyvXNI1CUGE/TlAIw0icqgI/AAAAAAAAANY/0PIQ6Gz5HDQ/2dappxrecon2.jpg)

View File

@ -1,10 +1,16 @@
//============================================================================
// Name : imagedemo1.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : DWT of arbitrary size image using symmetric or periodic extension
//============================================================================
# 2D DWT/IDWT Demo #
_Notes_
1. dwt\_2d and dwt\_2d\_sym functions are interchangeable in the following code as they take the same arguments.
2. Please make sure that right header file is included. Following sample program links to wavelet2d.h which is the header for shared libraries. wavelet2s.h must be included for static libraries.
3. I'm using [OPENCV](http://opencv.willowgarage.com/wiki/) to handle images as i already use OPENCV for other image processing work. You may want to use some simpler image libraries as OPENCV is a full image processing suite and is very bulky or you can just use 2D matrices/build your own image classes. Regardless, DWT/IDWT operations are more important than the choice of libraries.
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/wavelet2d/demo/imagedemo1.cpp)
```
#include <iostream>
#include <fstream>
@ -194,4 +200,17 @@ int main() {
cvSaveImage("recon.bmp",dvImg);
return 0;
}
}
```
Input Image is a low resolution 250X189 grayscale snow.jpg image.
![https://lh6.googleusercontent.com/-8t3vGld98oY/Tk-eBq7MV0I/AAAAAAAAAM8/4pxc03jqWk0/snow.jpg](https://lh6.googleusercontent.com/-8t3vGld98oY/Tk-eBq7MV0I/AAAAAAAAAM8/4pxc03jqWk0/snow.jpg)
_Input 250X189 Image_
![https://lh3.googleusercontent.com/-GE-XmAmDda0/Tk-eAqYxuFI/AAAAAAAAAMw/jxHLfz1g-1A/2ddwtout.jpg](https://lh3.googleusercontent.com/-GE-XmAmDda0/Tk-eAqYxuFI/AAAAAAAAAMw/jxHLfz1g-1A/2ddwtout.jpg)
_3-Level Decomposition using db3 wavelet_
![https://lh6.googleusercontent.com/-fYnS6T7nDeQ/Tk-eAmhETPI/AAAAAAAAAM0/8gFa8pXO46M/2ddwtrecon.jpg](https://lh6.googleusercontent.com/-fYnS6T7nDeQ/Tk-eAmhETPI/AAAAAAAAAM0/8gFa8pXO46M/2ddwtrecon.jpg)
_Perfectly Reconstructed Image_

View File

@ -1,10 +1,16 @@
//============================================================================
// Name : swt2Ddemo.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : 2D SWT Demo using OPENCV
//============================================================================
# 2D Stationary Wavelet Transform #
_Notes_
1. dwt\_2d and dwt\_2d\_sym functions are interchangeable in the following code as they take the same arguments.
2. Please make sure that right header file is included. Following sample program links to wavelet2d.h which is the header for shared libraries. wavelet2s.h must be included for static libraries.
3. I'm using OPENCV to handle images as i already use [OPENCV](http://opencv.willowgarage.com/wiki/) for other image processing work. You may want to use some simpler image libraries as OPENCV is a full image processing suite and is very bulky or you can just use 2D matrices/build your own image classes. Regardless, DWT/IDWT operations are more important than the choice of libraries.
[Sample Code](http://code.google.com/p/wavelet1d/source/browse/trunk/wavelet2d/demo/swt2Ddemo.cpp)
```
#include <iostream>
#include <fstream>
@ -85,7 +91,7 @@ int main() {
swt_2d(vec1,J,nm,output);
cout << "OUTPUT size" << output.size() << endl;
cout << "LOOP OK" << endl;
int row,col;
row=vec1.size();
col=vec1[0].size();
@ -171,4 +177,22 @@ int main() {
return 0;
}
}
```
Three level Stationary Wavelet Transform is computed using db2 wavelet. Approximation coefficients are stored only for the final (J=3) stage while the three detail coefficients( Horizontal, Vertical and Diagonal) are stored for each value. All 10 sets of coefficients are 512X512.
Input Image
![https://lh5.googleusercontent.com/-Y78s7sxlRcM/TlAItad_y4I/AAAAAAAAANM/fKDn4Um6Awo/lena512.jpg](https://lh5.googleusercontent.com/-Y78s7sxlRcM/TlAItad_y4I/AAAAAAAAANM/fKDn4Um6Awo/lena512.jpg)
Approximation Coefficient at level J = 3
![https://lh5.googleusercontent.com/-4E7Gtqj4MCs/TlAO_sX-kXI/AAAAAAAAANc/aXIMxdHv1Mw/blur.jpg](https://lh5.googleusercontent.com/-4E7Gtqj4MCs/TlAO_sX-kXI/AAAAAAAAANc/aXIMxdHv1Mw/blur.jpg)
Detail Coefficients at Levels 3,2,1(L-R). Coefficients are arranged Horizontally,Vertically and Diagonally from top to bottom.
![https://lh5.googleusercontent.com/-vqsGaPY5Pf8/TlAPFwwtzcI/AAAAAAAAANg/lV8npKIy_qc/s512/detail.jpg](https://lh5.googleusercontent.com/-vqsGaPY5Pf8/TlAPFwwtzcI/AAAAAAAAANg/lV8npKIy_qc/s512/detail.jpg)
_Resized Image (Actual Dimensions 1536X1536)_

279
newfunc.md Normal file
View File

@ -0,0 +1,279 @@
# List of Functions for wavelet2d Library #
## 1D DWT/IDWT Functions ##
Both periodic and symmetric extension methods for Decimated DWT take exactly same input arguments.The difference is that Output vector in periodic extension has usually the same size (~N) as the input vector(N) while output vector in symmetric extension case has redundancies with length depending on size of filter used.
### Periodic Extension ###
**1. DWT:** `void* dwt(vector<double> &sig, int J, string nm, vector<double> &dwt_output,vector<double> &flag, vector<int> &length )`
where,
_**sig**_ :: _Input Signal vector_
_**J**_ :: _Decomposition levels_
_**nm**_ :: _Wavelet Name_ _(See filtcoef for available wavelet families)_
_**length**_ :: _Lengths of respective approximation and detail vectors are stored in this integer vector._
_**dwt\_output**_ :: _Output of Discrete Wavelet Transform. It stores coefficients in following format:_
**`[A(J) D(J) D(J-1) ..... D(1)]`**
_where **A(J)** is the approximation coefficient vector at the Jth level while **D(n)** are the detail coefficient vectors at the nth level._**length**_contains the lengths of corresponding vectors. Last entry of the_**length**_vector is the length of the original signal._
_**flag**_ :: _Housekeeping vector. In this implementation it contains two values-_
_flag[0](0.md) is 0 if the signal is even and it is 1 if signal is odd and if it is made even by repeating the last value one more time_
_flag[1](1.md) - contains the decomposition levels._
_Housekeeping vector is a double vector as it was originally meant to store more values than it currently does_
![https://lh3.googleusercontent.com/-axX5BI71K7k/Tk7CvelHwrI/AAAAAAAAALI/Tc9h_KznCgM/s912/dwtperscreen.png](https://lh3.googleusercontent.com/-axX5BI71K7k/Tk7CvelHwrI/AAAAAAAAALI/Tc9h_KznCgM/s912/dwtperscreen.png)
_DWT stats (periodic extension) for an input signal of length 256_
**2. IDWT:** `void* idwt(vector<double> &dwtop,vector<double> &flag, string nm,vector<double> &idwt_output,vector<int> &length)`
where,
_**dwtop**_ :: _is the DWT vector_
_**flag**_ :: _Same Housekeeping function as obtained from the DWT function_
_**nm**_ :: _Wavelet Used_
_**idwt\_output**_ :: _Output of IDWT_
_**length**_ :: _Length vector obtained from the DWT computations_
### Symmetric Extension ###
**3. DWT:** `void* dwt_sym(vector<double> &sig, int J, string nm, vector<double> &dwt_output,vector<double> &flag, vector<int> &length )`
where,
_**sig**_ :: _Input Signal vector_
_**J**_ :: _Decomposition levels_
_**nm**_ :: _Wavelet Name_ _(See filtcoef for available wavelet families)_
_**length**_ :: _Lengths of respective approximation and detail vectors are stored in this integer vector._
_**dwt\_output**_ :: _Output of Discrete Wavelet Transform. It stores coefficients in following format:_
**`[A(J) D(J) D(J-1) ..... D(1)]`**
_where **A(J)** is the approximation coefficient vector at the Jth level while **D(n)** are the detail coefficient vectors at the nth level._**length**_contains the lengths of corresponding vectors. Last entry of the_**length**_vector is the length of the original signal._
_**flag**_ :: _Housekeeping vector. In this implementation it contains two values-_
_flag[0](0.md) is 0 if the signal is even and it is 1 if signal is odd and if it is made even by repeating the last value one more time_
_flag[1](1.md) - contains the decomposition levels._
_Housekeeping vector is a double vector as it was originally meant to store more values than it currently does_
_**idwt\_output**_ :: _Output of the Inverse Discrete Wavelet Transform_
_**length**_ :: _Length Vector Obtained from the DWT computations_
![https://lh5.googleusercontent.com/-rooeVHG4pdc/Tk7FP_sPOTI/AAAAAAAAALQ/xWTasj0blNE/s912/dwtsymscreen.png](https://lh5.googleusercontent.com/-rooeVHG4pdc/Tk7FP_sPOTI/AAAAAAAAALQ/xWTasj0blNE/s912/dwtsymscreen.png)
_DWT stats (symmetric extension) for an input signal of length 256_
**4. IDWT:** `void* idwt_sym(vector<double> &dwtop,vector<double> &flag, string nm,vector<double> &idwt_output,vector<int> &length)`
where,
_**dwtop**_ :: _is the DWT vector_
_**flag**_ :: _Same Housekeeping function as obtained from the DWT function_
_**nm**_ :: _Wavelet Used_
_**idwt\_output**_ :: _Output of IDWT_
_**length**_ :: _Length vector obtained from the DWT computations_
## 1D SWT/ISWT Functions ##
**5. SWT:** `void* swt(vector<double> &sig, int J, string nm, vector<double> &swt_output, int &length)`
> All the coefficients are of equal lengths and that value is stored in _**length**_. _**swt\_output**_ stores value in the same format as _**dwt**_ and _**dwt\_sym**_ functions - Approximation coefficient vector at level J is stored at the beginning of the **swt\_output** vector followed by detail coefficients vectors at levels J, J-1,...., 1. The signal length has to be divisible by 2^J for reliable results. You can use signal extension (see below) to make the lengths compatible with the SWT.
_Two Level SWT Decomposition of a 247 length signal vector_
**6. ISWT:** `void* iswt(vector<double> &swtop,int J, string nm, vector<double> &iswt_output)`
_**swtop**_ is the output of SWT stage , _**J**_ - number of levels and _**nm**_ is the wavelet as before. Output of ISWT is stored in _**iswt\_output**_ vector.
## 2D DWT/IDWT Functions ##
As in 1D case, both periodic and symmetric extension methods for Decimated DWT take exactly same input arguments.The difference is that Output vector in periodic extension has usually the same size (~NXN) as the input vector(NXN) while output vector in symmetric extension case has redundancies with length/breadth depending on size of filter used.
### Periodic Extension ###
**7. 2D DWT:** `void* dwt_2d(vector<vector<double> > &origsig, int J, string nm, vector<double> &dwt_output,vector<double> &flag, vector<int> &length) `
_**origsig**_ :: _Input Image/Matrix_
_**J**_ :: _Number of Decomposition Levels_
_**nm**_ :: _Wavelet Name_
_**flag**_ :: _Stores values for IDWT function.Only flag[0](0.md) value is important as it contains decomposition levels._
_**dwt\_output**_ :: _1D vector that stores the output in the following format
**A(J) D<sub>h</sub>(J) D<sub>v</sub>(J) D<sub>d</sub>(J) ..... D<sub>h</sub>(1) D<sub>v</sub>(1) D<sub>d</sub>(1)**_
where _**A(J)**_ is the approximation coefficient vector at the Jth level while _**D(n)**_ are the three detail coefficient vectors(horizontal,vertical and detail) at the nth level. It is important to remember that approximation and detail coefficients are actually two dimensional so we need a length vector that stores rows and columns values of each coefficient element. The length vector is given by _**length**_.
For example, the first element of _**output**_ vector is the approximation matrix stored as a vector and the first two elements of _**length**_ vectors are row and column values of the approximation matrix. In other words, a 300 element approximation matrix ( 15 rows X 20 columns) can be extracted from the 300 element approximation vector.
![https://lh3.googleusercontent.com/-mQm6JsFSDSE/Tk7eqaNPhLI/AAAAAAAAALY/CF70J_UuJOk/s912/dwt2dperscreen.png](https://lh3.googleusercontent.com/-mQm6JsFSDSE/Tk7eqaNPhLI/AAAAAAAAALY/CF70J_UuJOk/s912/dwt2dperscreen.png)
_2D DWT computation using periodic extension_
**8. 2D IDWT:** `void* idwt_2d(vector<double> &dwtop,vector<double> &flag, string nm,vector<vector<double> > &idwt_output, vector<int> &length)`
where,
_**dwtop**_ :: _is the DWT vector_
_**flag**_ :: _Same Housekeeping function as obtained from the DWT function_
_**nm**_ :: _Wavelet Used_
_**idwt\_output**_ :: _Output of IDWT which should be defined to have the same number of rows and columns as the input image/matrix_
_**length**_ :: _Length vector obtained from the DWT computations_
### Symmetric Extension ###
**9. 2D DWT:** `void* dwt_2d_sym(vector<vector<double> > &origsig, int J, string nm, vector<double> &dwt_output,vector<double> &flag, vector<int> &length) `
_**origsig**_ :: _Input Image/Matrix_
_**J**_ :: _Number of Decomposition Levels_
_**nm**_ :: _Wavelet Name_
_**flag**_ :: _Stores values for IDWT function.Only flag[0](0.md) value is important as it contains decomposition levels._
_**dwt\_output**_ :: _1D vector that stores the output in the following format
**A(J) D<sub>h</sub>(J) D<sub>v</sub>(J) D<sub>d</sub>(J) ..... D<sub>h</sub>(1) D<sub>v</sub>(1) D<sub>d</sub>(1)**_
where _**A(J)**_ is the approximation coefficient vector at the Jth level while _**D(n)**_ are the three detail coefficient vectors(horizontal,vertical and detail) at the nth level. It is important to remember that approximation and detail coefficients are actually two dimensional so we need a length vector that stores rows and columns values of each coefficient element. The length vector is given by _**length**_.
For example, the first element of _**output**_ vector is the approximation matrix stored as a vector and the first two elements of _**length**_ vectors are row and column values of the approximation matrix. In other words, a 300 element approximation matrix ( 15 rows X 20 columns) can be extracted from the 300 element approximation vector.
![https://lh3.googleusercontent.com/-H_5vbaS10FY/Tk7i3pyq5jI/AAAAAAAAALc/8ajg-QiCjpk/s912/dwt2dsymscreen.png](https://lh3.googleusercontent.com/-H_5vbaS10FY/Tk7i3pyq5jI/AAAAAAAAALc/8ajg-QiCjpk/s912/dwt2dsymscreen.png)
_2D DWT computation using symmetric extension_
**10. 2D IDWT:** `void* idwt_2d_sym(vector<double> &dwtop,vector<double> &flag, string nm,vector<vector<double> > &idwt_output, vector<int> &length)`
where,
_**dwtop**_ :: _is the DWT vector_
_**flag**_ :: _Same Housekeeping function as obtained from the DWT function_
_**nm**_ :: _Wavelet Used_
_**idwt\_output**_ :: _Output of IDWT which should be defined to have the same number of rows and columns as the input image/matrix_
_**length**_ :: _Length vector obtained from the DWT computations_
## 2D SWT Function ##
**11. 2D SWT:** `void* swt_2d(vector<vector<double> > &sig,int J, string nm, vector<double> &swt_output)`
_**swt\_output**_ is a 1D vector which is arranged the same way as DWT output vector in the Decimated 2D cases above except that in this case all coefficients are of same size. This is a highly redundant transform as a three level decomposition of a 512X512 image results in 10 512X512 images - one approximation image and 9 detail images (three at each level).
## Convolution ##
**12. Convolution FFT\_ESTIMATE (Recommended):** `double convfft(vector<double> &a, vector<double> &b, vector<double> &c)`
Convolution function is pretty straightforward. _**a**_ and _**b**_ are input vectors and _**c**_ is the convolution output. _**convfft**_ uses FFT so it gives better results in most cases than the regular convolution which is implemented by _**convol**_ function.
**13. Convolution Direct** (Use it for only smaller vectors)**:** `double convol(vector<double> &a, vector<double> &b, vector<double> &c)`
**14. Convolution FFT\_MEASURE** (Recommended if you are going to perform convolutions of same length hundreds or thousands of time in one program)**:** `double convfftm(vector<double> &a, vector<double> &b, vector<double> &c)`
_**convfftm**_ is performed using MEASUREing capabilities of FFTW3 library so it is not recommended if you are going to convolve two vectors only once. This has some overhead but gives good results if multiple instances of same convolution are performed repeatedly.
## Wavelet Filters ##
**15. Filters:** `int filtcoef(string nm, vector<double> &lpd, vector<double> &hpd, vector<double> &lpr, vector<double> &hpr)`
_**nm:**_ Wavelet name.
_**lpd:**_ Low Pass Decomposition Filter Coefficients.
_**hpd:**_ High Pass Decomposition Filter Coefficients.
_**lpr:**_ Low Pass Reconstruction Filter Coefficients.
_**hpr:**_ High Pass Reconstruction Filter Coefficients.
All filters are `vector<double>` objects and can be obtained by specifying the wavelet name. Currently, following Wavelets are available:
_**Daubechies :**_ db1,db2,.., ,db15
_**Biorthogonal:**_ bior1.1 ,bior1.3 ,bior1.5 ,bior2.2 ,bior2.4 ,bior2.6 ,bior2.8 ,bior3.1 ,bior3.3 ,bior3.5 ,bior3.7 ,bior3.9 ,bior4.4 ,bior5.5 ,bior6.8
_**Coiflets:**_ coif1,coif2,coif3,coif4,coif5
_**Symmlets:**_ sym2,........, sym10
## 1D Vector Manipulation ##
**16. Downsampling:** `void downsamp(vector<double> &sig, int M, vector<double> &sig_d)`
_**sig**_ :: Signal to be Downsampled
_**M**_ :: Downsampling factor
_**sig\_d**_ :: Downsampled signal
**17. Upsampling:** `void upsamp(vector<double> &sig, int M, vector<double> &sig_u)`
_**sig**_ :: Signal to be Upsampled
_**M**_ :: Upsampling factor
_**sig\_u**_ :: Upsampled signal
**18. Periodic Extension:** `void* per_ext(vector<double> &sig, int a) `
_**per\_ext**_ periodically extends the signal _**sig**_ by value _**a**_ in either direction.
**19. Symmetric Extension:** `void* symm_ext(vector<double> &sig, int a) `
_**symm\_ext**_ symmetrically extensd the signal _**sig**_ by value _**a**_ in either direction. This function needs refinement as it doesn't gives good results for smaller vectors.
## 2D Vector Manipulation ##
**20. 2D Downsampling:** `void* downsamp2(vector<vector<double> > & vec1,vector<vector<double> > & vec2, int rows_dn, int cols_dn) `
_**vec1**_ is the input, _**rows\_dn**_ and _**cols\_dn**_ are row and column downsampling factors. _**vec2**_ is the downsampled matrix.
**21. 2D Upsampling:** `void* upsamp2(vector<vector<double> > & vec1,vector<vector<double> > & vec2, int rows_up, int cols_up)`
_**vec1**_ is the input, _**rows\_up**_ and _**cols\_up**_ are row and column upsampling factors. _**vec2**_ is the upsampled matrix.
**22. 2D Periodic Extension:** `void* per_ext2d(vector<vector<double> > &signal,vector<vector<double> > &temp2, int a)`
_**signal**_ is extended by **_a_** in all directions and the result is returned in 2D vector _**temp2**_
**23. 2D Symmetric Extension:** `void* symm_ext2d(vector<vector<double> > &signal,vector<vector<double> > &temp2, int a)`
_**signal**_ is extended by **_a_** in all directions and the result is returned in 2D vector _**temp2**_

31
previous.md Normal file
View File

@ -0,0 +1,31 @@
I have added a DWT GUI for windows user :: [dyadwaves ](http://code.google.com/p/dyadwaves/). Any feedback will be appreciated.
# 1D/2D Discrete Wavelet Transform Implementation in C++ #
1. 1D DWT and IDWT Implementation (Two Modes)
1. 2D DWT and IDWT Implementation (Two Modes)
1. 1D SWT and ISWT Implementation ( Stationary Wavelet Transform)
1. 2D SWT Implementation
1. Implemented using Danielson Lanczos FFT Algorithm
Libraries (Compiled using MinGW and MSVC++ 2010 compilers in Windows) are available in Downloads section while source code is available in the source "src" folder.
The libraries and source codes are available at http://code.google.com/p/wavelet1d/. I have tried to make this a more "user-friendly" implementation by keeping the functions as simple and descriptive as possible. Additionally, the 1D DWT/IDWT routines will output data that can be used easily with GNUPLOT. It causes redundancy and possibly some clutter if signal files are large but ,in my opinion, the trade-off is worth it. The accompanying script also works best only when DWT and IDWT routines are called in the same program.
I have used C++ vector objects to accept input, store and output data. This is done to overcome certain programming limitations associated with using arrays. Dynamic arrays were also an option but they require a lot of house-cleaning without having any advantages over vector objects. To learn more about vectors, please refer to excellent tutorial at http://www.cplusplus.com/reference/stl/vector/ Vectors and Arrays can be converted back and forth so even if you are more comfortable with arrays, using vectors should not really be a problem.
|**[List of Functions](http://code.google.com/p/wavelet1d/wiki/Functions)**| Lists all Functions available in the Library|
|:-------------------------------------------------------------------------|:--------------------------------------------|
|**[Example Code 1](http://code.google.com/p/wavelet1d/wiki/1DDWTdemo)**| 1D DWT/IDWT Demo Code|
|**[Example Code 2](http://code.google.com/p/wavelet1d/wiki/1DAppx)**| 1D Signal Approximation Demo|
|**[Example Code 3](http://code.google.com/p/wavelet1d/wiki/2DDWTdemo)**| 2D DWT/IDWT Demo Code|
|**[Example Code 4](http://code.google.com/p/wavelet1d/wiki/2DAppx)**| Image Approximation Demo|
|**[Example Code 5](http://code.google.com/p/wavelet1d/wiki/2DSWTdemo)**| 2D SWT Demo Code|
|**[Example Code 6](http://code.google.com/p/wavelet1d/wiki/1DSWTDemo)**| 1D SWT Demo Code|
![https://lh4.googleusercontent.com/-4w-fWQyoieo/Thn_s7qb8-I/AAAAAAAAAGs/B0HFvLru6CU/s512/empire.jpg](https://lh4.googleusercontent.com/-4w-fWQyoieo/Thn_s7qb8-I/AAAAAAAAAGs/B0HFvLru6CU/s512/empire.jpg)
_J=2 Level Discrete Wavelet Transform of a 569X800 image using dwt\_2d\_sym function (Resized here for Display)_
Image Processing Note : I have not implemented any image class in C++ as of yet so I'm using OPENCV to handle images. It happens to be a rather bulky package and if you are not already working in image processing area, there are other more convenient options that may be used to handle simple image operations( loading, displaying, saving and converting them to c++ STL formats).

View File

@ -1,58 +0,0 @@
#
aux_source_directory(lib/ WAVELETLIB_SRC)
#
include_directories(/usr/local/include)
#
#
set(EXECUTABLE_OUTPUT_PATH ${PROJECT_BINARY_DIR}/bin)
#
#
# libcmake
add_library(wlet SHARED ${WAVELETLIB_SRC})
#
add_library(wlet_static STATIC ${WAVELETLIB_SRC})
#
set_target_properties(wlet_static PROPERTIES OUTPUT_NAME "wlet")
#
set_target_properties(wlet PROPERTIES CLEAN_DIRECT_OUTPUT 1)
set_target_properties(wlet_static PROPERTIES CLEAN_DIRECT_OUTPUT 1)
#
set_target_properties(wlet PROPERTIES VERSION 1.0 SOVERSION 1.0)
#
set(LIBRARY_OUTPUT_PATH ${PROJECT_BINARY_DIR}/lib)
find_library(FFTW_LIB fftw3 HINTS /usr/local/lib)
find_library(FFTW_A_LIB libfftw3.a HINTS /usr/local/lib)
target_link_libraries(wlet PUBLIC ${FFTW_LIB})
target_link_libraries(wlet_static ${FFTW_A_LIB})
#
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} --std=c++11 -O2")
#
install(TARGETS wlet wlet_static
LIBRARY DESTINATION lib
ARCHIVE DESTINATION lib)
#
install(FILES lib/wlet.h DESTINATION include)
#
macro(add_sample name)
#
include_directories(/usr/local/include/opencv4)
#
add_executable(${name} sample/${name}.cpp)
#
set_target_properties(${name} PROPERTIES INSTALL_RPATH "/usr/local/lib")
#
target_link_libraries(${name} PUBLIC wlet)
endmacro()
#
add_sample(swtdemo)
#add_sample(swt2Ddemo)
#add_sample(wavedemo)
#add_sample(imagedemo)

File diff suppressed because it is too large Load Diff

View File

@ -1,155 +0,0 @@
#ifndef WAVELET2D_H
#define WAVELET2D_H
#include <vector>
#include <complex>
using namespace std;
// 1D Functions
void* dwt1(string, vector<double> &, vector<double> &, vector<double> &);
void* dyadic_zpad_1d(vector<double> &);
double convol(vector<double> &, vector<double> &, vector<double> &);
int filtcoef(string , vector<double> &, vector<double> &, vector<double> &,
vector<double> &);
void downsamp(vector<double> &, int , vector<double> &);
void upsamp(vector<double> &, int, vector<double> &);
void circshift(vector<double> &, int );
int sign(int);
void* idwt1(string wname, vector<double> &, vector<double> &, vector<double> &);
int vecsum(vector<double> &, vector<double> &, vector<double> &);
// 1D Symmetric Extension DWT Functions
void* dwt_sym(vector<double> &, int ,string , vector<double> &,vector<double> &,
vector<int> &);
void* dwt1_sym(string , vector<double> &, vector<double> &, vector<double> &);
void* idwt_sym(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
void* symm_ext(vector<double> &, int );
void* idwt1_sym(string, vector<double> &, vector<double> &, vector<double> &); // Not Tested
// 1D Stationary Wavelet Transform
void* swt(vector<double> &, int , string , vector<double> &, int &) ;
void* iswt(vector<double> &,int , string, vector<double> &);
void* per_ext(vector<double> &, int );
// 2D Functions
void* branch_lp_dn(string , vector<double> &, vector<double> &);
void* branch_hp_dn(string , vector<double> &, vector<double> &);
void* branch_lp_hp_up(string ,vector<double> &, vector<double> &, vector<double> &);
//void* dwt_2d(vector<vector<double> > &, int , string , vector<vector<double> > &
// , vector<double> &) ;
//void* idwt_2d(vector<vector<double> > &,vector<double> &, string ,vector<vector<double> > &);
void* dyadic_zpad_2d(vector<vector<double> > &,vector<vector<double> > &);
void* dwt_output_dim(vector<vector<double> >&, int &, int & );
void* zero_remove(vector<vector<double> > &,vector<vector<double> > &) ;
void* getcoeff2d(vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &,vector<vector<double> > &,vector<double> &, int &);
void* idwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
void* dwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
void* downsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
void* upsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
// 2D DWT (Symmetric Extension) Functions
void* dwt_2d_sym(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
void* dwt2_sym(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
void* idwt_2d_sym(vector<double> &,vector<double> &, string ,vector<vector<double> > &,
vector<int> &);
void* circshift2d(vector<vector<double> > &, int , int );
void symm_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
void* dispDWT(vector<double> &,vector<vector<double> > &, vector<int> &, vector<int> &, int ) ;
void* dwt_output_dim_sym(vector<int> &,vector<int> &, int );
//2D Stationary Wavelet Transform
void* swt_2d(vector<vector<double> > &,int , string , vector<double> &);
void* per_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
// FFT functions
double convfft(vector<double> &, vector<double> &, vector<double> &);
double convfftm(vector<double> &, vector<double> &, vector<double> &);
void* fft(vector<complex<double> > &,int ,unsigned int);
void* bitreverse(vector<complex<double> > &);
void* freq(vector<double> &, vector<double> &);
//New
void* dwt1_sym_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD);//FFTW3 for 2D
void* idwt1_sym_m(string wname, vector<double> &X, vector<double> &app, vector<double> &detail);
void* dwt(vector<double> &sig, int J, string nm, vector<double> &dwt_output
, vector<double> &flag, vector<int> &length );
void* idwt(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
void* dwt_2d(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
void* dwt1_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD) ;
void* idwt_2d(vector<double> &dwtop,vector<double> &flag, string nm,
vector<vector<double> > &idwt_output, vector<int> &length);
void* idwt1_m(string wname, vector<double> &X, vector<double> &cA, vector<double> &cD);
void* dwt_output_dim2(vector<int> &length, vector<int> &length2, int J);
#endif/* WAVELET2D_H */

View File

@ -1,197 +0,0 @@
//============================================================================
// Name : imagedemo1.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : DWT of arbitrary size image using symmetric or periodic extension
//============================================================================
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <complex>
#include <cmath>
#include <algorithm>
#include "../lib/wlet2d.h"
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"
using namespace std;
using namespace cv;
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
void* maxval1(vector<double> &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
if (max <= arr[i]){
max = arr[i];
}
}
return 0;
}
int main() {
IplImage* img = cvLoadImage("snow.jpg");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
cvShowImage("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
cvSaveImage("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
string nm = "db3";
vector<double> l1,h1,l2,h2;
filtcoef(nm,l1,h1,l2,h2);
// unsigned int lf=l1.size();
// int rows_n =(int) (rows+ J*(lf-1));
// int cols_n =(int) (cols + J * ( lf -1));
// Finding 2D DWT Transform of the image using symetric extension algorithm
// Extension is set to 3 (eg., int e = 3)
vector<int> length;
vector<double> output,flag;
int J =3;
dwt_2d_sym(vec1,J,nm,output,flag,length);
double max;
vector<int> length2;
// This algorithm computes DWT of image of any given size. Together with convolution and
// subsampling operations it is clear that subsampled images are of different length than
// dyadic length images. In order to compute the "effective" size of DWT we do additional
// calculations.
dwt_output_dim_sym(length,length2,J);
// length2 is gives the integer vector that contains the size of subimages that will
// combine to form the displayed output image. The last two entries of length2 gives the
// size of DWT ( rows_n by cols_n)
int siz = length2.size();
int rows_n=length2[siz-2];
int cols_n = length2[siz-1];
vector<vector< double> > dwtdisp(rows_n, vector<double>(cols_n));
dispDWT(output,dwtdisp, length ,length2, J);
// dispDWT returns the 2D object dwtdisp which will be displayed using OPENCV's image
// handling functions
vector<vector<double> > dwt_output= dwtdisp;
maxval(dwt_output,max);// max value is needed to take care of overflow which happens because
// of convolution operations performed on unsigned 8 bit images
//Displaying Scaled Image
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = cols_n;
imgSize.height = rows_n;
cvImg = cvCreateImage( imgSize, 8, 1 );
// dwt_hold is created to hold the dwt output as further operations need to be
// carried out on dwt_output in order to display scaled images.
vector<vector<double> > dwt_hold(rows_n, vector<double>( cols_n));
dwt_hold = dwt_output;
// Setting coefficients of created image to the scaled DWT output values
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( dwt_output[i][j] <= 0.0){
dwt_output[i][j] = 0.0;
}
if ( i <= (length2[0]) && j <= (length2[1]) ) {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (dwt_output[i][j] / max) * 255.0);
} else {
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) (dwt_output[i][j]) ;
}
}
}
cvNamedWindow( "DWT Image", 1 ); // creation of a visualisation window
cvShowImage( "DWT Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("DWT Image");
cvSaveImage("dwt.bmp",cvImg);
// Finding IDWT
vector<vector<double> > idwt_output(rows, vector<double>(cols));
idwt_2d_sym(output,flag, nm, idwt_output,length);
//Displaying Reconstructed Image
IplImage *dvImg;
CvSize dvSize; // size of output image
dvSize.width = idwt_output[0].size();
dvSize.height = idwt_output.size();
cout << idwt_output.size() << idwt_output[0].size() << endl;
dvImg = cvCreateImage( dvSize, 8, 1 );
for (int i = 0; i < dvSize.height; i++ )
for (int j = 0; j < dvSize.width; j++ )
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) (idwt_output[i][j]) ;
cvNamedWindow( "Reconstructed Image", 1 ); // creation of a visualisation window
cvShowImage( "Reconstructed Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("Reconstructed Image");
cvSaveImage("recon.bmp",dvImg);
return 0;
}

View File

@ -1,178 +0,0 @@
//============================================================================
// Name : swt2Ddemo.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : 2D SWT Demo using OPENCV
//============================================================================
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <complex>
#include <cmath>
#include <algorithm>
#include "../lib/wlet2d.h"
#include <opencv2/opencv.hpp>
#include <opencv2/imgproc/imgproc_c.h>
#include <opencv2/imgproc/types_c.h>
#include <opencv2/highgui/highgui_c.h>
//#include "cv.h"
//#include "highgui.h"
//#include "cxcore.h"
using namespace std;
using namespace cv;
void* maxval(vector<vector<double> > &arr, double &max){
max = 0;
for (unsigned int i =0; i < arr.size(); i++) {
for (unsigned int j =0; j < arr[0].size(); j++) {
if (max <= arr[i][j]){
max = arr[i][j];
}
}
}
return 0;
}
int main() {
Mat img = imread("lena512.bmp");
if (!img){
cout << " Can't read Image. Try Different Format." << endl;
exit(1);
}
int height, width;
height = img->height;
width = img->width;
int nc = img->nChannels;
// uchar* ptr2 =(uchar*) img->imageData;
int pix_depth = img->depth;
CvSize size;
size.width =width;
size.height=height;
cout << "depth" << pix_depth << "Channels" << nc << endl;
cvNamedWindow("Original Image", CV_WINDOW_AUTOSIZE);
imshow("Original Image", img);
cvWaitKey();
cvDestroyWindow("Original Image");
imwrite("orig.bmp",img);
int rows =(int) height;
int cols =(int) width;
Mat matimg(img);
vector<vector<double> > vec1(rows, vector<double>(cols));
int k =1;
for (int i=0; i < rows; i++) {
for (int j =0; j < cols; j++){
unsigned char temp;
temp = ((uchar*) matimg.data + i * matimg.step)[j * matimg.elemSize() + k ];
vec1[i][j] = (double) temp;
}
}
string nm = "db2";
// vector<double> l1,h1,l2,h2;
// filtcoef(nm,l1,h1,l2,h2);
vector<double> output;
int J =3;
swt_2d(vec1,J,nm,output);
cout << "OUTPUT size" << output.size() << endl;
cout << "LOOP OK" << endl;
int row,col;
row=vec1.size();
col=vec1[0].size();
// Extract and Display Low Pass Image at the Jth stage
vector<vector<double> > blur(row,vector<double>(col));
for (int i=0;i < row; i++){
for (int j=0; j < col;j++){
double temp = output[i*col + j];
blur[i][j]= temp;
}
}
double max;
maxval(blur,max);
// Creating Image in OPENCV
IplImage *cvImg; // image used for output
CvSize imgSize; // size of output image
imgSize.width = col;
imgSize.height = row;
cvImg = cvCreateImage( imgSize, 8, 1 );
for (int i = 0; i < imgSize.height; i++ ) {
for (int j = 0; j < imgSize.width; j++ ){
if ( blur[i][j] <= 0.0){
blur[i][j] = 0.0;
}
((uchar*)(cvImg->imageData + cvImg->widthStep*i))[j] =
(char) ( (blur[i][j] / max) * 255.0);
}
}
cvNamedWindow( "Low Pass Image", 1 ); // creation of a visualisation window
imshow( "Low Pass Image", cvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("Low Pass Image");
imwrite("blur.bmp",cvImg);
// Displaying BandPass Images
vector<vector<double> > detail(3*row,vector<double>(J * col));
for (int k=0; k < J; k++) {
for (int i=0; i < 3*row; i++) {
for(int j=0+ k*col; j < (k+1)*col; j++) {
double temp = output[(3*k+1)*row*col+ i * col +j - k*col];
detail[i][j]= temp;
}
}
}
Mat dvImg; // image used for output
CvSize imgSz; // size of output image
imgSz.width = J*col;
imgSz.height = 3*row;
dvImg = cvCreateImage( imgSz, 8, 1 );
for (int i = 0; i < imgSz.height; i++ ) {
for (int j = 0; j < imgSz.width; j++ ){
if ( detail[i][j] <= 0.0){
detail[i][j] = 0.0;
}
((uchar*)(dvImg->imageData + dvImg->widthStep*i))[j] =
(char) detail[i][j];
}
}
cvNamedWindow( "Band Pass Image", 1 ); // creation of a visualisation window
imshow( "Band Pass Image", dvImg ); // image visualisation
cvWaitKey();
cvDestroyWindow("Band Pass Image");
imwrite("detail.bmp",dvImg);
return 0;
}

View File

@ -1,93 +0,0 @@
//============================================================================
// Name : swtdemo.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : 1D Stationary Wavelet Transform Demo
//============================================================================
#include <iostream>
#include <fstream>
#include "../lib/wlet2d.h"
#include <vector>
#include <string>
#include <cmath>
using namespace std;
int main() {
cout << "********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********" << endl; // prints
cout << "This program accepts signal from the user in a file format " << endl;
cout << "and performs Discrete Wavelet Transform with specified " << endl;
cout << "wavelet. " << endl;
cout << " " << endl;
cout << " The Following Wavelets are in the Database: " << endl;
cout << " haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10, " << endl;
cout << " db11, db12, db13, db14, db15. " << endl;
cout << " bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8, " << endl;
cout << " bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4," << endl;
cout << " bior5.5, bior6.8." << endl;
cout << " coif1, coif2, coif3, coif4, coif5." << endl;
cout << "Please Enter the Wavelet Name at the Prompt( No quotes) :" << endl;
string nm; // nm will store the name of Wavelet Family
cin >> nm;
cout << "Enter the name of signal file at the Prompt eg., signal.txt :" << endl;
char inp[50];
cin >> inp;
vector<double> sig;
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
}
while (sig_inp) {
double temp;
sig_inp >> temp;
sig.push_back(temp);
}
sig.pop_back();
vector<double> original;
original = sig; // Make a copy of the signal if you want to use original signal
// later on. The other option is to use IDWT output as the SWt/ISWT system is
// Perefect Reconstruction system.
cout << "Please Enter the Number of DWT Stages J :" << endl;
int J;
cin >> J ;
vector<double> swt_output;
// perform J-Level DWT
int length;// All coefficients are of same length. Variable "length" returns length
// of coefficients. It is not required for ISWT computations.
swt(sig, J, nm, swt_output, length);
cout << "coeff-len = " << length << endl;
ofstream swtcoeff("swtcoeff.txt");
for (unsigned int i=0; i < swt_output.size(); i++) {
swtcoeff << swt_output[i] << endl;
}
// remove high level details
for (int i = 0; i < 200; i++)
{
swt_output[200+i] = 0.0;
}
vector<double> iswt_output;
iswt(swt_output,J, nm,iswt_output);
ofstream sig1("recon.txt");
ofstream diff("diff.txt");
cout <<" Recon signal size" << iswt_output.size() << endl;
for (unsigned int i = 0; i < iswt_output.size(); i++){
sig1 << iswt_output[i] << " " << original[i] << endl;
diff << iswt_output[i] - original[i] << endl;
}
return 0;
}

View File

@ -1,83 +0,0 @@
//============================================================================
// Name : wavedemo1.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : 1D DWT Demo
//============================================================================
#include <iostream>
#include <fstream>
#include "../lib/wlet2d.h"
#include <vector>
#include <string>
#include <cmath>
using namespace std;
int main() {
cout << "********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********" << endl; // prints
cout << "This program accepts signal from the user in a file format " << endl;
cout << "and performs Discrete Wavelet Transform with specified " << endl;
cout << "wavelet. " << endl;
cout << " " << endl;
cout << " The Following Wavelets are in the Database: " << endl;
cout << " haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10, " << endl;
cout << " db11, db12, db13, db14, db15. " << endl;
cout << " bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8, " << endl;
cout << " bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4," << endl;
cout << " bior5.5, bior6.8." << endl;
cout << " coif1, coif2, coif3, coif4, coif5." << endl;
cout << "Please Enter the Wavelet Name at the Prompt( No quotes) :" << endl;
string nm; // nm will store the name of Wavelet Family
cin >> nm;
cout << "Enter the name of signal file at the Prompt eg., signal.txt :" << endl;
char inp[50];
cin >> inp;
vector<double> sig;
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
}
while (sig_inp) {
double temp;
sig_inp >> temp;
sig.push_back(temp);
}
sig.pop_back();
vector<double> original;
original = sig;
cout << "Please Enter the Number of DWT Stages J :" << endl;
int J;
cin >> J ;
vector<double> dwt_output, flag;
// perform J-Level DWT
vector<int> length;
dwt_sym(sig, J, nm, dwt_output,flag,length);
ofstream dwtout("dwtout.txt");
for (unsigned int i = 0; i < dwt_output.size(); i++){
dwtout << dwt_output[i] << endl;
}
//Perform J-Level IDWT
vector<double> output;
idwt_sym(dwt_output, flag,nm,output,length);
ofstream sig1("recon.txt");
ofstream diff("diff.txt");
cout <<" Recon signal size" << output.size() << endl;
for (unsigned int i = 0; i < output.size(); i++){
sig1 << output[i] << endl;
diff << output[i] - original[i] << endl;
}
//gnudwtplot(J);
return 0;
}

View File

@ -1 +0,0 @@
# Deprecated Code. See the Wavelet2d folder for the latest code (wavelet2d.h and wavelet2d.cpp files)

View File

@ -1,9 +0,0 @@
ver 0.3
A couple of major changes and a few minor tweaks.
1. Periodic DWT code changed. The issue was Perfect Reconstruction wasn't working when filter length became larger than
decmated signal. Code changed to implement actual periodic extension instead of using circular shift to mimic periodic
extension. Change is strictly under the hood and header file remains unchanged.
2. Dyadic Zero padding is changed to padding the signal by the last value of the signal instead of zeros.

View File

@ -1,340 +0,0 @@
GNU GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1989, 1991 Free Software Foundation, Inc.
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. This
General Public License applies to most of the Free Software
Foundation's software and to any other program whose authors commit to
using it. (Some other Free Software Foundation software is covered by
the GNU Library General Public License instead.) You can apply it to
your programs, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must show them these terms so they know their
rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that redistributors of a free
program will individually obtain patent licenses, in effect making the
program proprietary. To prevent this, we have made it clear that any
patent must be licensed for everyone's free use or not licensed at all.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License applies to any program or other work which contains
a notice placed by the copyright holder saying it may be distributed
under the terms of this General Public License. The "Program", below,
refers to any such program or work, and a "work based on the Program"
means either the Program or any derivative work under copyright law:
that is to say, a work containing the Program or a portion of it,
either verbatim or with modifications and/or translated into another
language. (Hereinafter, translation is included without limitation in
the term "modification".) Each licensee is addressed as "you".
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running the Program is not restricted, and the output from the Program
is covered only if its contents constitute a work based on the
Program (independent of having been made by running the Program).
Whether that is true depends on what the Program does.
1. You may copy and distribute verbatim copies of the Program's
source code as you receive it, in any medium, provided that you
conspicuously and appropriately publish on each copy an appropriate
copyright notice and disclaimer of warranty; keep intact all the
notices that refer to this License and to the absence of any warranty;
and give any other recipients of the Program a copy of this License
along with the Program.
You may charge a fee for the physical act of transferring a copy, and
you may at your option offer warranty protection in exchange for a fee.
2. You may modify your copy or copies of the Program or any portion
of it, thus forming a work based on the Program, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) You must cause the modified files to carry prominent notices
stating that you changed the files and the date of any change.
b) You must cause any work that you distribute or publish, that in
whole or in part contains or is derived from the Program or any
part thereof, to be licensed as a whole at no charge to all third
parties under the terms of this License.
c) If the modified program normally reads commands interactively
when run, you must cause it, when started running for such
interactive use in the most ordinary way, to print or display an
announcement including an appropriate copyright notice and a
notice that there is no warranty (or else, saying that you provide
a warranty) and that users may redistribute the program under
these conditions, and telling the user how to view a copy of this
License. (Exception: if the Program itself is interactive but
does not normally print such an announcement, your work based on
the Program is not required to print an announcement.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Program,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Program, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Program.
In addition, mere aggregation of another work not based on the Program
with the Program (or with a work based on the Program) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may copy and distribute the Program (or a work based on it,
under Section 2) in object code or executable form under the terms of
Sections 1 and 2 above provided that you also do one of the following:
a) Accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of Sections
1 and 2 above on a medium customarily used for software interchange; or,
b) Accompany it with a written offer, valid for at least three
years, to give any third party, for a charge no more than your
cost of physically performing source distribution, a complete
machine-readable copy of the corresponding source code, to be
distributed under the terms of Sections 1 and 2 above on a medium
customarily used for software interchange; or,
c) Accompany it with the information you received as to the offer
to distribute corresponding source code. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form with such
an offer, in accord with Subsection b above.)
The source code for a work means the preferred form of the work for
making modifications to it. For an executable work, complete source
code means all the source code for all modules it contains, plus any
associated interface definition files, plus the scripts used to
control compilation and installation of the executable. However, as a
special exception, the source code distributed need not include
anything that is normally distributed (in either source or binary
form) with the major components (compiler, kernel, and so on) of the
operating system on which the executable runs, unless that component
itself accompanies the executable.
If distribution of executable or object code is made by offering
access to copy from a designated place, then offering equivalent
access to copy the source code from the same place counts as
distribution of the source code, even though third parties are not
compelled to copy the source along with the object code.
4. You may not copy, modify, sublicense, or distribute the Program
except as expressly provided under this License. Any attempt
otherwise to copy, modify, sublicense or distribute the Program is
void, and will automatically terminate your rights under this License.
However, parties who have received copies, or rights, from you under
this License will not have their licenses terminated so long as such
parties remain in full compliance.
5. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Program or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Program (or any work based on the
Program), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Program or works based on it.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the
original licensor to copy, distribute or modify the Program subject to
these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
7. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Program at all. For example, if a patent
license would not permit royalty-free redistribution of the Program by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Program.
If any portion of this section is held invalid or unenforceable under
any particular circumstance, the balance of the section is intended to
apply and the section as a whole is intended to apply in other
circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system, which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
8. If the distribution and/or use of the Program is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Program under this License
may add an explicit geographical distribution limitation excluding
those countries, so that distribution is permitted only in or among
countries not thus excluded. In such case, this License incorporates
the limitation as if written in the body of this License.
9. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of this License which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
this License, you may choose any version ever published by the Free Software
Foundation.
10. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to the public, the best way to achieve this is to make it
free software which everyone can redistribute and change under these terms.
To do so, attach the following notices to the program. It is safest
to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least
the "copyright" line and a pointer to where the full notice is found.
<one line to give the program's name and a brief idea of what it does.>
Copyright (C) <year> <name of author>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Also add information on how to contact you by electronic and paper mail.
If the program is interactive, make it output a short notice like this
when it starts in an interactive mode:
Gnomovision version 69, Copyright (C) year name of author
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the appropriate
parts of the General Public License. Of course, the commands you use may
be called something other than `show w' and `show c'; they could even be
mouse-clicks or menu items--whatever suits your program.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the program, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
`Gnomovision' (which makes passes at compilers) written by James Hacker.
<signature of Ty Coon>, 1 April 1989
Ty Coon, President of Vice
This General Public License does not permit incorporating your program into
proprietary programs. If your program is a subroutine library, you may
consider it more useful to permit linking proprietary applications with the
library. If this is what you want to do, use the GNU Library General
Public License instead of this License.

View File

@ -1 +0,0 @@
-18.3237 -18.2232 -18.0974 -17.9410 -17.7480 -17.5113 -17.2230 -16.8744 -16.4558 -15.9565 -15.3653 -14.6701 -13.8586 -12.9182 -11.8363 -10.6008 -9.2006 -7.6257 -5.8680 -3.9217 -1.7839 0.5452 3.0614 5.7562 8.6167 11.6252 14.7591 17.9909 21.2884 24.6155 27.9319 31.1947 34.3587 37.3775 40.2049 42.7957 13.2164 14.2125 15.0317 15.6595 16.0845 16.2990 16.2990 16.0845 15.6595 15.0317 14.2125 13.2164 12.0608 10.7654 9.3517 34.3587 31.1947 27.9319 24.6155 21.2884 17.9909 14.7591 11.6252 8.6167 5.7562 3.0614 0.5452 -1.7839 -3.9217 -5.8680 -7.6257 -9.2006 -10.6008 -11.8363 -12.9182 -13.8586 -14.6701 -15.3653 -15.9565 -16.4558 -16.8744 -17.2230 -17.5113 -17.7480 -17.9410 -18.0974 -18.2232 -18.3237 -18.4035 -18.0080 -17.8889 -17.7403 -17.5533 -17.3156 -17.0102 -16.6129 -16.0884 -15.3848 -14.4239 -13.0840 -11.1708 -8.3634 -4.1098 2.5833 13.6048 32.7934 28.0187 10.9660 1.0776 -4.9459 -8.7354 -11.1225 -12.4865 -12.8019 -11.2050 -3.3124 1.8995 -11.3573 -15.0684 -16.5028 -17.1937 -17.5831 -17.8288 -17.9968 -18.1185 -18.2103 -18.2818 -18.3388 -18.3849 -18.4229 -18.4545 -18.4810 -17.4642 -17.2104 -16.9033 -16.5317 -16.0822 -15.5384 -14.8804 -14.0844 -13.1214 -11.9563 -10.5467 -8.8414 -6.7782 -4.2822 -1.2624 2.3911 6.8111 12.1585 18.6280 26.4549 35.9241 35.9241 26.4549 18.6280 12.1585 6.8111 2.3911 -1.2624 -4.2822 -6.7782 -8.8414 -10.5467 -11.9563 -13.1214 -14.0844 -14.8804 -15.5384 -16.0822 -16.5317 -16.9033 -17.2104 -17.4642 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 34.8066 34.6752 34.5285 34.3645 34.1812 33.9763 33.7474 33.4917 33.2058 32.8863 32.5294 32.1304 31.6846 31.1864 30.6296 30.0074 29.3121 28.5350 27.6667 26.6963 25.6118 24.3999 23.0456 21.5322 19.8408 17.9507 15.8385 13.4781 10.8403 7.8925 4.5982 0.9168 -3.1972 -7.7947 -12.9325 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.3237

File diff suppressed because it is too large Load Diff

View File

@ -1,32 +0,0 @@
/*
* wave1d.h
*
* Created on: Feb 26, 2011
* Author: Rafat Hussain
*/
#ifndef WAVE1D_H_
#define WAVE1D_H_
#include <vector>
using namespace std;
void* dwt(vector<double> &, int ,string , vector<double> &, vector<double> &);
void* dwt1(string, vector<double> &, vector<double> &, vector<double> &);
void* dyadic_zpad_1d(vector<double> &);
double convol(vector<double> &, vector<double> &, vector<double> &);
int filtcoef(string , vector<double> &, vector<double> &, vector<double> &,
vector<double> &);
void downsamp(vector<double> &, int , vector<double> &);
void upsamp(vector<double> &, int, vector<double> &);
void circshift(vector<double> &, int );
int sign(int);
void* gnudwtplot(int);
void* idwt(vector<double> &,vector<double> &, string , vector<double> &) ;
void* idwt1(string wname, vector<double> &, vector<double> &, vector<double> &);
int vecsum(vector<double> &, vector<double> &, vector<double> &);
#endif /* WAVE1D_H_ */

File diff suppressed because it is too large Load Diff

View File

@ -1,142 +0,0 @@
/*
* wavelet.h
*
* Created on: April 11, 2011
* Author: Rafat Hussain
*/
#ifndef WAVELET_H_
#define WAVELET_H_
#include <vector>
#include <complex>
using namespace std;
// 1D Functions
void* dwt(vector<double> &, int ,string , vector<double> &, vector<double> &);
void* dwt1(string, vector<double> &, vector<double> &, vector<double> &);
void* dyadic_zpad_1d(vector<double> &);
double convol(vector<double> &, vector<double> &, vector<double> &);
int filtcoef(string , vector<double> &, vector<double> &, vector<double> &,
vector<double> &);
void downsamp(vector<double> &, int , vector<double> &);
void upsamp(vector<double> &, int, vector<double> &);
void circshift(vector<double> &, int );
int sign(int);
void* gnudwtplot(int);
void* idwt(vector<double> &,vector<double> &, string , vector<double> &) ;
void* idwt1(string wname, vector<double> &, vector<double> &, vector<double> &);
int vecsum(vector<double> &, vector<double> &, vector<double> &);
// 1D Symmetric Extension DWT Functions
void* dwt_sym(vector<double> &, int ,string , vector<double> &,vector<double> &,
vector<int> &, int );
void* dwt1_sym(string , vector<double> &, vector<double> &, vector<double> &);
void* idwt_sym(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
void* symm_ext(vector<double> &, int );
void* idwt1_sym(string, vector<double> &, vector<double> &, vector<double> &); // Not Tested
// 1D Stationary Wavelet Transform
void* swt(vector<double> &, int , string , vector<double> &, int &) ;
void* iswt(vector<double> &,int , string, vector<double> &);
void* gnuswtplot(int );
void* per_ext(vector<double> &, int );
// 2D Functions
void* branch_lp_dn(string , vector<double> &, vector<double> &);
void* branch_hp_dn(string , vector<double> &, vector<double> &);
void* branch_lp_hp_up(string ,vector<double> &, vector<double> &, vector<double> &);
void* dwt_2d(vector<vector<double> > &, int , string , vector<vector<double> > &
, vector<double> &) ;
void* idwt_2d(vector<vector<double> > &,vector<double> &, string ,vector<vector<double> > &);
void* dyadic_zpad_2d(vector<vector<double> > &,vector<vector<double> > &);
void* dwt_output_dim(vector<vector<double> >&, int &, int & );
void* zero_remove(vector<vector<double> > &,vector<vector<double> > &) ;
void* getcoeff2d(vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &,vector<vector<double> > &,vector<double> &, int &);
void* idwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
void* dwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
void* downsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
void* upsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
// 2D DWT (Symmetric Extension) Functions
void* dwt_2d_sym(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &, int );
void* dwt2_sym(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
void* idwt_2d_sym(vector<double> &,vector<double> &, string ,vector<vector<double> > &,
vector<int> &);
void* circshift2d(vector<vector<double> > &, int , int );
void symm_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
void* dispDWT(vector<double> &,vector<vector<double> > &, vector<int> &, vector<int> &, int ) ;
void* dwt_output_dim_sym(vector<int> &,vector<int> &, int );
//2D Stationary Wavelet Transform
void* swt_2d(vector<vector<double> > &,int , string , vector<double> &);
void* per_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
// FFT functions
double convfft(vector<double> &, vector<double> &, vector<double> &);
void* fft(vector<complex<double> > &,int ,unsigned int);
void* bitreverse(vector<complex<double> > &);
void* freq(vector<double> &, vector<double> &);
#endif /* WAVELET_H_ */

BIN
wavedemo1-1.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 23 KiB

View File

@ -1,4 +0,0 @@
This git repository does not contain the FFTW package. It is recommended that you download the full working packages
for windows and linux from http://wavelet2d.sourceforge.net and https://sourceforge.net/projects/wavelet2d/files/.
Alternatively, you can clone this git repository and build the FFTW package on your computer. See documentation at
https://sourceforge.net/projects/wavelet2d/files/

View File

@ -1,14 +0,0 @@
Notes
1.dwt and dwt_sym functions are interchangeable in all the codes as they take the same arguments.
2.Please make sure that right header file is included. Header file for dynamic libraries is
wavelet2d.h and for static libraries, wavelet2s.h is used.
3.I’m using OPENCV to handle images as i already use OPENCV for other image processing work. You may
want to use some simpler image libraries as OPENCV is a full image processing suite and is very
bulky or you can just use 2D matrices/build your own image classes. Regardless, DWT/IDWT operations
are more important than the choice of libraries.
4.All updated example codes are available at
http://code.google.com/p/wavelet1d/source/browse/trunk/wavelet2d/demo/

View File

@ -1 +0,0 @@
-18.3237 -18.2232 -18.0974 -17.9410 -17.7480 -17.5113 -17.2230 -16.8744 -16.4558 -15.9565 -15.3653 -14.6701 -13.8586 -12.9182 -11.8363 -10.6008 -9.2006 -7.6257 -5.8680 -3.9217 -1.7839 0.5452 3.0614 5.7562 8.6167 11.6252 14.7591 17.9909 21.2884 24.6155 27.9319 31.1947 34.3587 37.3775 40.2049 42.7957 13.2164 14.2125 15.0317 15.6595 16.0845 16.2990 16.2990 16.0845 15.6595 15.0317 14.2125 13.2164 12.0608 10.7654 9.3517 34.3587 31.1947 27.9319 24.6155 21.2884 17.9909 14.7591 11.6252 8.6167 5.7562 3.0614 0.5452 -1.7839 -3.9217 -5.8680 -7.6257 -9.2006 -10.6008 -11.8363 -12.9182 -13.8586 -14.6701 -15.3653 -15.9565 -16.4558 -16.8744 -17.2230 -17.5113 -17.7480 -17.9410 -18.0974 -18.2232 -18.3237 -18.4035 -18.0080 -17.8889 -17.7403 -17.5533 -17.3156 -17.0102 -16.6129 -16.0884 -15.3848 -14.4239 -13.0840 -11.1708 -8.3634 -4.1098 2.5833 13.6048 32.7934 28.0187 10.9660 1.0776 -4.9459 -8.7354 -11.1225 -12.4865 -12.8019 -11.2050 -3.3124 1.8995 -11.3573 -15.0684 -16.5028 -17.1937 -17.5831 -17.8288 -17.9968 -18.1185 -18.2103 -18.2818 -18.3388 -18.3849 -18.4229 -18.4545 -18.4810 -17.4642 -17.2104 -16.9033 -16.5317 -16.0822 -15.5384 -14.8804 -14.0844 -13.1214 -11.9563 -10.5467 -8.8414 -6.7782 -4.2822 -1.2624 2.3911 6.8111 12.1585 18.6280 26.4549 35.9241 35.9241 26.4549 18.6280 12.1585 6.8111 2.3911 -1.2624 -4.2822 -6.7782 -8.8414 -10.5467 -11.9563 -13.1214 -14.0844 -14.8804 -15.5384 -16.0822 -16.5317 -16.9033 -17.2104 -17.4642 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 6.3259 34.8066 34.6752 34.5285 34.3645 34.1812 33.9763 33.7474 33.4917 33.2058 32.8863 32.5294 32.1304 31.6846 31.1864 30.6296 30.0074 29.3121 28.5350 27.6667 26.6963 25.6118 24.3999 23.0456 21.5322 19.8408 17.9507 15.8385 13.4781 10.8403 7.8925 4.5982 0.9168 -3.1972 -7.7947 -12.9325 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.6741 -18.3237

View File

@ -1,83 +0,0 @@
//============================================================================
// Name : wavedemo1.cpp
// Author : Rafat Hussain
// Version :
// Copyright :
// Description : 1D DWT Demo
//============================================================================
#include <iostream>
#include <fstream>
#include "wavelet2d.h"
#include <vector>
#include <string>
#include <cmath>
using namespace std;
int main() {
cout << "********J- LEVEL DISCRETE WAVELET TRANSFORM IMPLEMENTATION*********" << endl; // prints
cout << "This program accepts signal from the user in a file format " << endl;
cout << "and performs Discrete Wavelet Transform with specified " << endl;
cout << "wavelet. " << endl;
cout << " " << endl;
cout << " The Following Wavelets are in the Database: " << endl;
cout << " haar, db1, db2, db3, db4, db5, db6, db7, db8, db9, db10, " << endl;
cout << " db11, db12, db13, db14, db15. " << endl;
cout << " bior1.1, bio1.3, bior1.5, bior2.2, bior2.4,bior2.6,bior2.8, " << endl;
cout << " bior3.1, bior3.3, bior3.5, bior3.7, bior3.9, bior4.4," << endl;
cout << " bior5.5, bior6.8." << endl;
cout << " coif1, coif2, coif3, coif4, coif5." << endl;
cout << "Please Enter the Wavelet Name at the Prompt( No quotes) :" << endl;
string nm; // nm will store the name of Wavelet Family
cin >> nm;
cout << "Enter the name of signal file at the Prompt eg., signal.txt :" << endl;
char inp[50];
cin >> inp;
vector<double> sig;
ifstream sig_inp(inp);
if ( !sig_inp.good()){
cout << "The File doesn't exist"<< endl;
}
while (sig_inp) {
double temp;
sig_inp >> temp;
sig.push_back(temp);
}
sig.pop_back();
vector<double> original;
original = sig;
cout << "Please Enter the Number of DWT Stages J :" << endl;
int J;
cin >> J ;
vector<double> dwt_output, flag;
// perform J-Level DWT
vector<int> length;
dwt_sym(sig, J, nm, dwt_output,flag,length);
ofstream dwtout("dwtout.txt");
for (unsigned int i = 0; i < dwt_output.size(); i++){
dwtout << dwt_output[i] << endl;
}
//Perform J-Level IDWT
vector<double> output;
idwt_sym(dwt_output, flag,nm,output,length);
ofstream sig1("recon.txt");
ofstream diff("diff.txt");
cout <<" Recon signal size" << output.size() << endl;
for (unsigned int i = 0; i < output.size(); i++){
sig1 << output[i] << endl;
diff << output[i] - original[i] << endl;
}
//gnudwtplot(J);
return 0;
}

File diff suppressed because it is too large Load Diff

View File

@ -1,162 +0,0 @@
#ifndef WAVELET2D_H
#define WAVELET2D_H
#include <vector>
#include <complex>
using namespace std;
// the dll exports
#if defined WAVE_EXPORT
#define EXPORT __declspec(dllexport)
#else
#define EXPORT __declspec(dllimport)
#endif
// 1D Functions
EXPORT void* dwt1(string, vector<double> &, vector<double> &, vector<double> &);
EXPORT void* dyadic_zpad_1d(vector<double> &);
EXPORT double convol(vector<double> &, vector<double> &, vector<double> &);
EXPORT int filtcoef(string , vector<double> &, vector<double> &, vector<double> &,
vector<double> &);
EXPORT void downsamp(vector<double> &, int , vector<double> &);
EXPORT void upsamp(vector<double> &, int, vector<double> &);
EXPORT void circshift(vector<double> &, int );
EXPORT int sign(int);
EXPORT void* idwt1(string wname, vector<double> &, vector<double> &, vector<double> &);
EXPORT int vecsum(vector<double> &, vector<double> &, vector<double> &);
// 1D Symmetric Extension DWT Functions
EXPORT void* dwt_sym(vector<double> &, int ,string , vector<double> &,vector<double> &,
vector<int> &);
EXPORT void* dwt1_sym(string , vector<double> &, vector<double> &, vector<double> &);
EXPORT void* idwt_sym(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
EXPORT void* symm_ext(vector<double> &, int );
EXPORT void* idwt1_sym(string, vector<double> &, vector<double> &, vector<double> &); // Not Tested
// 1D Stationary Wavelet Transform
EXPORT void* swt(vector<double> &, int , string , vector<double> &, int &) ;
EXPORT void* iswt(vector<double> &,int , string, vector<double> &);
EXPORT void* per_ext(vector<double> &, int );
// 2D Functions
EXPORT void* branch_lp_dn(string , vector<double> &, vector<double> &);
EXPORT void* branch_hp_dn(string , vector<double> &, vector<double> &);
EXPORT void* branch_lp_hp_up(string ,vector<double> &, vector<double> &, vector<double> &);
//EXPORT void* dwt_2d(vector<vector<double> > &, int , string , vector<vector<double> > &
// , vector<double> &) ;
//EXPORT void* idwt_2d(vector<vector<double> > &,vector<double> &, string ,vector<vector<double> > &);
EXPORT void* dyadic_zpad_2d(vector<vector<double> > &,vector<vector<double> > &);
EXPORT void* dwt_output_dim(vector<vector<double> >&, int &, int & );
EXPORT void* zero_remove(vector<vector<double> > &,vector<vector<double> > &) ;
EXPORT void* getcoeff2d(vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &,vector<vector<double> > &,vector<double> &, int &);
EXPORT void* idwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* dwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* downsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
EXPORT void* upsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
// 2D DWT (Symmetric Extension) Functions
EXPORT void* dwt_2d_sym(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
EXPORT void* dwt2_sym(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* idwt_2d_sym(vector<double> &,vector<double> &, string ,vector<vector<double> > &,
vector<int> &);
EXPORT void* circshift2d(vector<vector<double> > &, int , int );
EXPORT void symm_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
EXPORT void* dispDWT(vector<double> &,vector<vector<double> > &, vector<int> &, vector<int> &, int ) ;
EXPORT void* dwt_output_dim_sym(vector<int> &,vector<int> &, int );
//2D Stationary Wavelet Transform
EXPORT void* swt_2d(vector<vector<double> > &,int , string , vector<double> &);
EXPORT void* per_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
// FFT functions
EXPORT double convfft(vector<double> &, vector<double> &, vector<double> &);
EXPORT double convfftm(vector<double> &, vector<double> &, vector<double> &);
EXPORT void* fft(vector<complex<double> > &,int ,unsigned int);
EXPORT void* bitreverse(vector<complex<double> > &);
EXPORT void* freq(vector<double> &, vector<double> &);
//New
EXPORT void* dwt1_sym_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD);//FFTW3 for 2D
EXPORT void* idwt1_sym_m(string wname, vector<double> &X, vector<double> &app, vector<double> &detail);
EXPORT void* dwt(vector<double> &sig, int J, string nm, vector<double> &dwt_output
, vector<double> &flag, vector<int> &length );
EXPORT void* idwt(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
EXPORT void* dwt_2d(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
EXPORT void* dwt1_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD) ;
EXPORT void* idwt_2d(vector<double> &dwtop,vector<double> &flag, string nm,
vector<vector<double> > &idwt_output, vector<int> &length);
EXPORT void* idwt1_m(string wname, vector<double> &X, vector<double> &cA, vector<double> &cD);
EXPORT void* dwt_output_dim2(vector<int> &length, vector<int> &length2, int J);
#endif/* WAVELET2D_H */

File diff suppressed because it is too large Load Diff

View File

@ -1,155 +0,0 @@
#ifndef WAVELET2S_H
#define WAVELET2S_H
#include <vector>
#include <complex>
using namespace std;
// 1D Functions
// void* dwt(vector<double> &, int ,string , vector<double> &, vector<double> &);
void* dwt1(string, vector<double> &, vector<double> &, vector<double> &);
void* dyadic_zpad_1d(vector<double> &);
double convol(vector<double> &, vector<double> &, vector<double> &);
int filtcoef(string , vector<double> &, vector<double> &, vector<double> &,
vector<double> &);
void downsamp(vector<double> &, int , vector<double> &);
void upsamp(vector<double> &, int, vector<double> &);
void circshift(vector<double> &, int );
int sign(int);
void* idwt1(string wname, vector<double> &, vector<double> &, vector<double> &);
int vecsum(vector<double> &, vector<double> &, vector<double> &);
// 1D Symmetric Extension DWT Functions
void* dwt_sym(vector<double> &, int ,string , vector<double> &,vector<double> &,
vector<int> &);
void* dwt1_sym(string , vector<double> &, vector<double> &, vector<double> &);
void* idwt_sym(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
void* symm_ext(vector<double> &, int );
void* idwt1_sym(string, vector<double> &, vector<double> &, vector<double> &); // Not Tested
// 1D Stationary Wavelet Transform
void* swt(vector<double> &, int , string , vector<double> &, int &) ;
void* iswt(vector<double> &,int , string, vector<double> &);
void* per_ext(vector<double> &, int );
// 2D Functions
void* branch_lp_dn(string , vector<double> &, vector<double> &);
void* branch_hp_dn(string , vector<double> &, vector<double> &);
void* branch_lp_hp_up(string ,vector<double> &, vector<double> &, vector<double> &);
// void* dwt_2d(vector<vector<double> > &, int , string , vector<vector<double> > &
// , vector<double> &) ;
// void* idwt_2d(vector<vector<double> > &,vector<double> &, string ,vector<vector<double> > &);
void* dyadic_zpad_2d(vector<vector<double> > &,vector<vector<double> > &);
void* dwt_output_dim(vector<vector<double> >&, int &, int & );
void* zero_remove(vector<vector<double> > &,vector<vector<double> > &) ;
void* getcoeff2d(vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &,vector<vector<double> > &,vector<double> &, int &);
void* idwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
void* dwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
void* downsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
void* upsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
// 2D DWT (Symmetric Extension) Functions
void* dwt_2d_sym(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
void* dwt2_sym(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
void* idwt_2d_sym(vector<double> &,vector<double> &, string ,vector<vector<double> > &,
vector<int> &);
void* circshift2d(vector<vector<double> > &, int , int );
void symm_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
void* dispDWT(vector<double> &,vector<vector<double> > &, vector<int> &, vector<int> &, int ) ;
void* dwt_output_dim_sym(vector<int> &,vector<int> &, int );
//2D Stationary Wavelet Transform
void* swt_2d(vector<vector<double> > &,int , string , vector<double> &);
void* per_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
// FFT functions
double convfft(vector<double> &, vector<double> &, vector<double> &);
double convfftm(vector<double> &, vector<double> &, vector<double> &);
void* fft(vector<complex<double> > &,int ,unsigned int);
void* bitreverse(vector<complex<double> > &);
void* freq(vector<double> &, vector<double> &);
//New
void* dwt1_sym_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD);//FFTW3 for 2D
void* idwt1_sym_m(string wname, vector<double> &X, vector<double> &app, vector<double> &detail);
void* dwt(vector<double> &sig, int J, string nm, vector<double> &dwt_output
, vector<double> &flag, vector<int> &length );
void* idwt(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
void* dwt_2d(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
void* dwt1_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD) ;
void* idwt_2d(vector<double> &dwtop,vector<double> &flag, string nm,
vector<vector<double> > &idwt_output, vector<int> &length);
void* idwt1_m(string wname, vector<double> &X, vector<double> &cA, vector<double> &cD);
void* dwt_output_dim2(vector<int> &length, vector<int> &length2, int J);
#endif/* WAVELET2S_H */

File diff suppressed because it is too large Load Diff

View File

@ -1,162 +0,0 @@
#ifndef WAVELET2D_H
#define WAVELET2D_H
#include <vector>
#include <complex>
using namespace std;
// the dll exports
#if defined WAVE_EXPORT
#define EXPORT __declspec(dllexport)
#else
#define EXPORT __declspec(dllimport)
#endif
// 1D Functions
EXPORT void* dwt1(string, vector<double> &, vector<double> &, vector<double> &);
EXPORT void* dyadic_zpad_1d(vector<double> &);
EXPORT double convol(vector<double> &, vector<double> &, vector<double> &);
EXPORT int filtcoef(string , vector<double> &, vector<double> &, vector<double> &,
vector<double> &);
EXPORT void downsamp(vector<double> &, int , vector<double> &);
EXPORT void upsamp(vector<double> &, int, vector<double> &);
EXPORT void circshift(vector<double> &, int );
EXPORT int sign(int);
EXPORT void* idwt1(string wname, vector<double> &, vector<double> &, vector<double> &);
EXPORT int vecsum(vector<double> &, vector<double> &, vector<double> &);
// 1D Symmetric Extension DWT Functions
EXPORT void* dwt_sym(vector<double> &, int ,string , vector<double> &,vector<double> &,
vector<int> &);
EXPORT void* dwt1_sym(string , vector<double> &, vector<double> &, vector<double> &);
EXPORT void* idwt_sym(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
EXPORT void* symm_ext(vector<double> &, int );
EXPORT void* idwt1_sym(string, vector<double> &, vector<double> &, vector<double> &); // Not Tested
// 1D Stationary Wavelet Transform
EXPORT void* swt(vector<double> &, int , string , vector<double> &, int &) ;
EXPORT void* iswt(vector<double> &,int , string, vector<double> &);
EXPORT void* per_ext(vector<double> &, int );
// 2D Functions
EXPORT void* branch_lp_dn(string , vector<double> &, vector<double> &);
EXPORT void* branch_hp_dn(string , vector<double> &, vector<double> &);
EXPORT void* branch_lp_hp_up(string ,vector<double> &, vector<double> &, vector<double> &);
//EXPORT void* dwt_2d(vector<vector<double> > &, int , string , vector<vector<double> > &
// , vector<double> &) ;
//EXPORT void* idwt_2d(vector<vector<double> > &,vector<double> &, string ,vector<vector<double> > &);
EXPORT void* dyadic_zpad_2d(vector<vector<double> > &,vector<vector<double> > &);
EXPORT void* dwt_output_dim(vector<vector<double> >&, int &, int & );
EXPORT void* zero_remove(vector<vector<double> > &,vector<vector<double> > &) ;
EXPORT void* getcoeff2d(vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &,vector<vector<double> > &,vector<double> &, int &);
EXPORT void* idwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* dwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* downsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
EXPORT void* upsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
// 2D DWT (Symmetric Extension) Functions
EXPORT void* dwt_2d_sym(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
EXPORT void* dwt2_sym(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* idwt_2d_sym(vector<double> &,vector<double> &, string ,vector<vector<double> > &,
vector<int> &);
EXPORT void* circshift2d(vector<vector<double> > &, int , int );
EXPORT void symm_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
EXPORT void* dispDWT(vector<double> &,vector<vector<double> > &, vector<int> &, vector<int> &, int ) ;
EXPORT void* dwt_output_dim_sym(vector<int> &,vector<int> &, int );
//2D Stationary Wavelet Transform
EXPORT void* swt_2d(vector<vector<double> > &,int , string , vector<double> &);
EXPORT void* per_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
// FFT functions
EXPORT double convfft(vector<double> &, vector<double> &, vector<double> &);
EXPORT double convfftm(vector<double> &, vector<double> &, vector<double> &);
EXPORT void* fft(vector<complex<double> > &,int ,unsigned int);
EXPORT void* bitreverse(vector<complex<double> > &);
EXPORT void* freq(vector<double> &, vector<double> &);
//New
EXPORT void* dwt1_sym_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD);//FFTW3 for 2D
EXPORT void* idwt1_sym_m(string wname, vector<double> &X, vector<double> &app, vector<double> &detail);
EXPORT void* dwt(vector<double> &sig, int J, string nm, vector<double> &dwt_output
, vector<double> &flag, vector<int> &length );
EXPORT void* idwt(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
EXPORT void* dwt_2d(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
EXPORT void* dwt1_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD) ;
EXPORT void* idwt_2d(vector<double> &dwtop,vector<double> &flag, string nm,
vector<vector<double> > &idwt_output, vector<int> &length);
EXPORT void* idwt1_m(string wname, vector<double> &X, vector<double> &cA, vector<double> &cD);
EXPORT void* dwt_output_dim2(vector<int> &length, vector<int> &length2, int J);
#endif/* WAVELET2D_H */

View File

@ -1,340 +0,0 @@
GNU GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1989, 1991 Free Software Foundation, Inc.
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. This
General Public License applies to most of the Free Software
Foundation's software and to any other program whose authors commit to
using it. (Some other Free Software Foundation software is covered by
the GNU Library General Public License instead.) You can apply it to
your programs, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must show them these terms so they know their
rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that redistributors of a free
program will individually obtain patent licenses, in effect making the
program proprietary. To prevent this, we have made it clear that any
patent must be licensed for everyone's free use or not licensed at all.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License applies to any program or other work which contains
a notice placed by the copyright holder saying it may be distributed
under the terms of this General Public License. The "Program", below,
refers to any such program or work, and a "work based on the Program"
means either the Program or any derivative work under copyright law:
that is to say, a work containing the Program or a portion of it,
either verbatim or with modifications and/or translated into another
language. (Hereinafter, translation is included without limitation in
the term "modification".) Each licensee is addressed as "you".
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running the Program is not restricted, and the output from the Program
is covered only if its contents constitute a work based on the
Program (independent of having been made by running the Program).
Whether that is true depends on what the Program does.
1. You may copy and distribute verbatim copies of the Program's
source code as you receive it, in any medium, provided that you
conspicuously and appropriately publish on each copy an appropriate
copyright notice and disclaimer of warranty; keep intact all the
notices that refer to this License and to the absence of any warranty;
and give any other recipients of the Program a copy of this License
along with the Program.
You may charge a fee for the physical act of transferring a copy, and
you may at your option offer warranty protection in exchange for a fee.
2. You may modify your copy or copies of the Program or any portion
of it, thus forming a work based on the Program, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) You must cause the modified files to carry prominent notices
stating that you changed the files and the date of any change.
b) You must cause any work that you distribute or publish, that in
whole or in part contains or is derived from the Program or any
part thereof, to be licensed as a whole at no charge to all third
parties under the terms of this License.
c) If the modified program normally reads commands interactively
when run, you must cause it, when started running for such
interactive use in the most ordinary way, to print or display an
announcement including an appropriate copyright notice and a
notice that there is no warranty (or else, saying that you provide
a warranty) and that users may redistribute the program under
these conditions, and telling the user how to view a copy of this
License. (Exception: if the Program itself is interactive but
does not normally print such an announcement, your work based on
the Program is not required to print an announcement.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Program,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Program, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Program.
In addition, mere aggregation of another work not based on the Program
with the Program (or with a work based on the Program) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may copy and distribute the Program (or a work based on it,
under Section 2) in object code or executable form under the terms of
Sections 1 and 2 above provided that you also do one of the following:
a) Accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of Sections
1 and 2 above on a medium customarily used for software interchange; or,
b) Accompany it with a written offer, valid for at least three
years, to give any third party, for a charge no more than your
cost of physically performing source distribution, a complete
machine-readable copy of the corresponding source code, to be
distributed under the terms of Sections 1 and 2 above on a medium
customarily used for software interchange; or,
c) Accompany it with the information you received as to the offer
to distribute corresponding source code. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form with such
an offer, in accord with Subsection b above.)
The source code for a work means the preferred form of the work for
making modifications to it. For an executable work, complete source
code means all the source code for all modules it contains, plus any
associated interface definition files, plus the scripts used to
control compilation and installation of the executable. However, as a
special exception, the source code distributed need not include
anything that is normally distributed (in either source or binary
form) with the major components (compiler, kernel, and so on) of the
operating system on which the executable runs, unless that component
itself accompanies the executable.
If distribution of executable or object code is made by offering
access to copy from a designated place, then offering equivalent
access to copy the source code from the same place counts as
distribution of the source code, even though third parties are not
compelled to copy the source along with the object code.
4. You may not copy, modify, sublicense, or distribute the Program
except as expressly provided under this License. Any attempt
otherwise to copy, modify, sublicense or distribute the Program is
void, and will automatically terminate your rights under this License.
However, parties who have received copies, or rights, from you under
this License will not have their licenses terminated so long as such
parties remain in full compliance.
5. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Program or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Program (or any work based on the
Program), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Program or works based on it.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the
original licensor to copy, distribute or modify the Program subject to
these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
7. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Program at all. For example, if a patent
license would not permit royalty-free redistribution of the Program by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Program.
If any portion of this section is held invalid or unenforceable under
any particular circumstance, the balance of the section is intended to
apply and the section as a whole is intended to apply in other
circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system, which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
8. If the distribution and/or use of the Program is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Program under this License
may add an explicit geographical distribution limitation excluding
those countries, so that distribution is permitted only in or among
countries not thus excluded. In such case, this License incorporates
the limitation as if written in the body of this License.
9. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of this License which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
this License, you may choose any version ever published by the Free Software
Foundation.
10. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to the public, the best way to achieve this is to make it
free software which everyone can redistribute and change under these terms.
To do so, attach the following notices to the program. It is safest
to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least
the "copyright" line and a pointer to where the full notice is found.
<one line to give the program's name and a brief idea of what it does.>
Copyright (C) <year> <name of author>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Also add information on how to contact you by electronic and paper mail.
If the program is interactive, make it output a short notice like this
when it starts in an interactive mode:
Gnomovision version 69, Copyright (C) year name of author
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the appropriate
parts of the General Public License. Of course, the commands you use may
be called something other than `show w' and `show c'; they could even be
mouse-clicks or menu items--whatever suits your program.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the program, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
`Gnomovision' (which makes passes at compilers) written by James Hacker.
<signature of Ty Coon>, 1 April 1989
Ty Coon, President of Vice
This General Public License does not permit incorporating your program into
proprietary programs. If your program is a subroutine library, you may
consider it more useful to permit linking proprietary applications with the
library. If this is what you want to do, use the GNU Library General
Public License instead of this License.

View File

@ -1,21 +0,0 @@
/*
* Copyright (c) 2011 Rafat Hussain
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.This program also uses FFTW3 library
* for high speed computation and it is being distributed in accordance
* with GNU-GPL license ver 2.0
* For FFTW3 copyright information, see the FFTW3 folder.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
*/

View File

@ -1,164 +0,0 @@
/*
Copyright (c) 2003-2010, Mark Borgerding
All rights reserved.
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
* Neither the author nor the names of any contributors may be used to endorse or promote products derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/* kiss_fft.h
defines kiss_fft_scalar as either short or a float type
and defines
typedef struct { kiss_fft_scalar r; kiss_fft_scalar i; }kiss_fft_cpx; */
#include "kiss_fft.h"
#include <limits.h>
#define MAXFACTORS 32
/* e.g. an fft of length 128 has 4 factors
as far as kissfft is concerned
4*4*4*2
*/
struct kiss_fft_state{
int nfft;
int inverse;
int factors[2*MAXFACTORS];
kiss_fft_cpx twiddles[1];
};
/*
Explanation of macros dealing with complex math:
C_MUL(m,a,b) : m = a*b
C_FIXDIV( c , div ) : if a fixed point impl., c /= div. noop otherwise
C_SUB( res, a,b) : res = a - b
C_SUBFROM( res , a) : res -= a
C_ADDTO( res , a) : res += a
* */
#ifdef FIXED_POINT
#if (FIXED_POINT==32)
# define FRACBITS 31
# define SAMPPROD int64_t
#define SAMP_MAX 2147483647
#else
# define FRACBITS 15
# define SAMPPROD int32_t
#define SAMP_MAX 32767
#endif
#define SAMP_MIN -SAMP_MAX
#if defined(CHECK_OVERFLOW)
# define CHECK_OVERFLOW_OP(a,op,b) \
if ( (SAMPPROD)(a) op (SAMPPROD)(b) > SAMP_MAX || (SAMPPROD)(a) op (SAMPPROD)(b) < SAMP_MIN ) { \
fprintf(stderr,"WARNING:overflow @ " __FILE__ "(%d): (%d " #op" %d) = %ld\n",__LINE__,(a),(b),(SAMPPROD)(a) op (SAMPPROD)(b) ); }
#endif
# define smul(a,b) ( (SAMPPROD)(a)*(b) )
# define sround( x ) (kiss_fft_scalar)( ( (x) + (1<<(FRACBITS-1)) ) >> FRACBITS )
# define S_MUL(a,b) sround( smul(a,b) )
# define C_MUL(m,a,b) \
do{ (m).r = sround( smul((a).r,(b).r) - smul((a).i,(b).i) ); \
(m).i = sround( smul((a).r,(b).i) + smul((a).i,(b).r) ); }while(0)
# define DIVSCALAR(x,k) \
(x) = sround( smul( x, SAMP_MAX/k ) )
# define C_FIXDIV(c,div) \
do { DIVSCALAR( (c).r , div); \
DIVSCALAR( (c).i , div); }while (0)
# define C_MULBYSCALAR( c, s ) \
do{ (c).r = sround( smul( (c).r , s ) ) ;\
(c).i = sround( smul( (c).i , s ) ) ; }while(0)
#else /* not FIXED_POINT*/
# define S_MUL(a,b) ( (a)*(b) )
#define C_MUL(m,a,b) \
do{ (m).r = (a).r*(b).r - (a).i*(b).i;\
(m).i = (a).r*(b).i + (a).i*(b).r; }while(0)
# define C_FIXDIV(c,div) /* NOOP */
# define C_MULBYSCALAR( c, s ) \
do{ (c).r *= (s);\
(c).i *= (s); }while(0)
#endif
#ifndef CHECK_OVERFLOW_OP
# define CHECK_OVERFLOW_OP(a,op,b) /* noop */
#endif
#define C_ADD( res, a,b)\
do { \
CHECK_OVERFLOW_OP((a).r,+,(b).r)\
CHECK_OVERFLOW_OP((a).i,+,(b).i)\
(res).r=(a).r+(b).r; (res).i=(a).i+(b).i; \
}while(0)
#define C_SUB( res, a,b)\
do { \
CHECK_OVERFLOW_OP((a).r,-,(b).r)\
CHECK_OVERFLOW_OP((a).i,-,(b).i)\
(res).r=(a).r-(b).r; (res).i=(a).i-(b).i; \
}while(0)
#define C_ADDTO( res , a)\
do { \
CHECK_OVERFLOW_OP((res).r,+,(a).r)\
CHECK_OVERFLOW_OP((res).i,+,(a).i)\
(res).r += (a).r; (res).i += (a).i;\
}while(0)
#define C_SUBFROM( res , a)\
do {\
CHECK_OVERFLOW_OP((res).r,-,(a).r)\
CHECK_OVERFLOW_OP((res).i,-,(a).i)\
(res).r -= (a).r; (res).i -= (a).i; \
}while(0)
#ifdef FIXED_POINT
# define KISS_FFT_COS(phase) floor(.5+SAMP_MAX * cos (phase))
# define KISS_FFT_SIN(phase) floor(.5+SAMP_MAX * sin (phase))
# define HALF_OF(x) ((x)>>1)
#elif defined(USE_SIMD)
# define KISS_FFT_COS(phase) _mm_set1_ps( cos(phase) )
# define KISS_FFT_SIN(phase) _mm_set1_ps( sin(phase) )
# define HALF_OF(x) ((x)*_mm_set1_ps(.5))
#else
# define KISS_FFT_COS(phase) (kiss_fft_scalar) cos(phase)
# define KISS_FFT_SIN(phase) (kiss_fft_scalar) sin(phase)
# define HALF_OF(x) ((x)*.5)
#endif
#define kf_cexp(x,phase) \
do{ \
(x)->r = KISS_FFT_COS(phase);\
(x)->i = KISS_FFT_SIN(phase);\
}while(0)
/* a debugging function */
#define pcpx(c)\
fprintf(stderr,"%g + %gi\n",(double)((c)->r),(double)((c)->i) )
#ifdef KISS_FFT_USE_ALLOCA
// define this to allow use of alloca instead of malloc for temporary buffers
// Temporary buffers are used in two case:
// 1. FFT sizes that have "bad" factors. i.e. not 2,3 and 5
// 2. "in-place" FFTs. Notice the quotes, since kissfft does not really do an in-place transform.
#include <alloca.h>
#define KISS_FFT_TMP_ALLOC(nbytes) alloca(nbytes)
#define KISS_FFT_TMP_FREE(ptr)
#else
#define KISS_FFT_TMP_ALLOC(nbytes) KISS_FFT_MALLOC(nbytes)
#define KISS_FFT_TMP_FREE(ptr) KISS_FFT_FREE(ptr)
#endif

View File

@ -1,408 +0,0 @@
/*
Copyright (c) 2003-2010, Mark Borgerding
All rights reserved.
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
* Neither the author nor the names of any contributors may be used to endorse or promote products derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "_kiss_fft_guts.h"
/* The guts header contains all the multiplication and addition macros that are defined for
fixed or floating point complex numbers. It also delares the kf_ internal functions.
*/
static void kf_bfly2(
kiss_fft_cpx * Fout,
const size_t fstride,
const kiss_fft_cfg st,
int m
)
{
kiss_fft_cpx * Fout2;
kiss_fft_cpx * tw1 = st->twiddles;
kiss_fft_cpx t;
Fout2 = Fout + m;
do{
C_FIXDIV(*Fout,2); C_FIXDIV(*Fout2,2);
C_MUL (t, *Fout2 , *tw1);
tw1 += fstride;
C_SUB( *Fout2 , *Fout , t );
C_ADDTO( *Fout , t );
++Fout2;
++Fout;
}while (--m);
}
static void kf_bfly4(
kiss_fft_cpx * Fout,
const size_t fstride,
const kiss_fft_cfg st,
const size_t m
)
{
kiss_fft_cpx *tw1,*tw2,*tw3;
kiss_fft_cpx scratch[6];
size_t k=m;
const size_t m2=2*m;
const size_t m3=3*m;
tw3 = tw2 = tw1 = st->twiddles;
do {
C_FIXDIV(*Fout,4); C_FIXDIV(Fout[m],4); C_FIXDIV(Fout[m2],4); C_FIXDIV(Fout[m3],4);
C_MUL(scratch[0],Fout[m] , *tw1 );
C_MUL(scratch[1],Fout[m2] , *tw2 );
C_MUL(scratch[2],Fout[m3] , *tw3 );
C_SUB( scratch[5] , *Fout, scratch[1] );
C_ADDTO(*Fout, scratch[1]);
C_ADD( scratch[3] , scratch[0] , scratch[2] );
C_SUB( scratch[4] , scratch[0] , scratch[2] );
C_SUB( Fout[m2], *Fout, scratch[3] );
tw1 += fstride;
tw2 += fstride*2;
tw3 += fstride*3;
C_ADDTO( *Fout , scratch[3] );
if(st->inverse) {
Fout[m].r = scratch[5].r - scratch[4].i;
Fout[m].i = scratch[5].i + scratch[4].r;
Fout[m3].r = scratch[5].r + scratch[4].i;
Fout[m3].i = scratch[5].i - scratch[4].r;
}else{
Fout[m].r = scratch[5].r + scratch[4].i;
Fout[m].i = scratch[5].i - scratch[4].r;
Fout[m3].r = scratch[5].r - scratch[4].i;
Fout[m3].i = scratch[5].i + scratch[4].r;
}
++Fout;
}while(--k);
}
static void kf_bfly3(
kiss_fft_cpx * Fout,
const size_t fstride,
const kiss_fft_cfg st,
size_t m
)
{
size_t k=m;
const size_t m2 = 2*m;
kiss_fft_cpx *tw1,*tw2;
kiss_fft_cpx scratch[5];
kiss_fft_cpx epi3;
epi3 = st->twiddles[fstride*m];
tw1=tw2=st->twiddles;
do{
C_FIXDIV(*Fout,3); C_FIXDIV(Fout[m],3); C_FIXDIV(Fout[m2],3);
C_MUL(scratch[1],Fout[m] , *tw1);
C_MUL(scratch[2],Fout[m2] , *tw2);
C_ADD(scratch[3],scratch[1],scratch[2]);
C_SUB(scratch[0],scratch[1],scratch[2]);
tw1 += fstride;
tw2 += fstride*2;
Fout[m].r = Fout->r - HALF_OF(scratch[3].r);
Fout[m].i = Fout->i - HALF_OF(scratch[3].i);
C_MULBYSCALAR( scratch[0] , epi3.i );
C_ADDTO(*Fout,scratch[3]);
Fout[m2].r = Fout[m].r + scratch[0].i;
Fout[m2].i = Fout[m].i - scratch[0].r;
Fout[m].r -= scratch[0].i;
Fout[m].i += scratch[0].r;
++Fout;
}while(--k);
}
static void kf_bfly5(
kiss_fft_cpx * Fout,
const size_t fstride,
const kiss_fft_cfg st,
int m
)
{
kiss_fft_cpx *Fout0,*Fout1,*Fout2,*Fout3,*Fout4;
int u;
kiss_fft_cpx scratch[13];
kiss_fft_cpx * twiddles = st->twiddles;
kiss_fft_cpx *tw;
kiss_fft_cpx ya,yb;
ya = twiddles[fstride*m];
yb = twiddles[fstride*2*m];
Fout0=Fout;
Fout1=Fout0+m;
Fout2=Fout0+2*m;
Fout3=Fout0+3*m;
Fout4=Fout0+4*m;
tw=st->twiddles;
for ( u=0; u<m; ++u ) {
C_FIXDIV( *Fout0,5); C_FIXDIV( *Fout1,5); C_FIXDIV( *Fout2,5); C_FIXDIV( *Fout3,5); C_FIXDIV( *Fout4,5);
scratch[0] = *Fout0;
C_MUL(scratch[1] ,*Fout1, tw[u*fstride]);
C_MUL(scratch[2] ,*Fout2, tw[2*u*fstride]);
C_MUL(scratch[3] ,*Fout3, tw[3*u*fstride]);
C_MUL(scratch[4] ,*Fout4, tw[4*u*fstride]);
C_ADD( scratch[7],scratch[1],scratch[4]);
C_SUB( scratch[10],scratch[1],scratch[4]);
C_ADD( scratch[8],scratch[2],scratch[3]);
C_SUB( scratch[9],scratch[2],scratch[3]);
Fout0->r += scratch[7].r + scratch[8].r;
Fout0->i += scratch[7].i + scratch[8].i;
scratch[5].r = scratch[0].r + S_MUL(scratch[7].r,ya.r) + S_MUL(scratch[8].r,yb.r);
scratch[5].i = scratch[0].i + S_MUL(scratch[7].i,ya.r) + S_MUL(scratch[8].i,yb.r);
scratch[6].r = S_MUL(scratch[10].i,ya.i) + S_MUL(scratch[9].i,yb.i);
scratch[6].i = -S_MUL(scratch[10].r,ya.i) - S_MUL(scratch[9].r,yb.i);
C_SUB(*Fout1,scratch[5],scratch[6]);
C_ADD(*Fout4,scratch[5],scratch[6]);
scratch[11].r = scratch[0].r + S_MUL(scratch[7].r,yb.r) + S_MUL(scratch[8].r,ya.r);
scratch[11].i = scratch[0].i + S_MUL(scratch[7].i,yb.r) + S_MUL(scratch[8].i,ya.r);
scratch[12].r = - S_MUL(scratch[10].i,yb.i) + S_MUL(scratch[9].i,ya.i);
scratch[12].i = S_MUL(scratch[10].r,yb.i) - S_MUL(scratch[9].r,ya.i);
C_ADD(*Fout2,scratch[11],scratch[12]);
C_SUB(*Fout3,scratch[11],scratch[12]);
++Fout0;++Fout1;++Fout2;++Fout3;++Fout4;
}
}
/* perform the butterfly for one stage of a mixed radix FFT */
static void kf_bfly_generic(
kiss_fft_cpx * Fout,
const size_t fstride,
const kiss_fft_cfg st,
int m,
int p
)
{
int u,k,q1,q;
kiss_fft_cpx * twiddles = st->twiddles;
kiss_fft_cpx t;
int Norig = st->nfft;
kiss_fft_cpx * scratch = (kiss_fft_cpx*)KISS_FFT_TMP_ALLOC(sizeof(kiss_fft_cpx)*p);
for ( u=0; u<m; ++u ) {
k=u;
for ( q1=0 ; q1<p ; ++q1 ) {
scratch[q1] = Fout[ k ];
C_FIXDIV(scratch[q1],p);
k += m;
}
k=u;
for ( q1=0 ; q1<p ; ++q1 ) {
int twidx=0;
Fout[ k ] = scratch[0];
for (q=1;q<p;++q ) {
twidx += fstride * k;
if (twidx>=Norig) twidx-=Norig;
C_MUL(t,scratch[q] , twiddles[twidx] );
C_ADDTO( Fout[ k ] ,t);
}
k += m;
}
}
KISS_FFT_TMP_FREE(scratch);
}
static
void kf_work(
kiss_fft_cpx * Fout,
const kiss_fft_cpx * f,
const size_t fstride,
int in_stride,
int * factors,
const kiss_fft_cfg st
)
{
kiss_fft_cpx * Fout_beg=Fout;
const int p=*factors++; /* the radix */
const int m=*factors++; /* stage's fft length/p */
const kiss_fft_cpx * Fout_end = Fout + p*m;
#ifdef _OPENMP
// use openmp extensions at the
// top-level (not recursive)
if (fstride==1 && p<=5)
{
int k;
// execute the p different work units in different threads
# pragma omp parallel for
for (k=0;k<p;++k)
kf_work( Fout +k*m, f+ fstride*in_stride*k,fstride*p,in_stride,factors,st);
// all threads have joined by this point
switch (p) {
case 2: kf_bfly2(Fout,fstride,st,m); break;
case 3: kf_bfly3(Fout,fstride,st,m); break;
case 4: kf_bfly4(Fout,fstride,st,m); break;
case 5: kf_bfly5(Fout,fstride,st,m); break;
default: kf_bfly_generic(Fout,fstride,st,m,p); break;
}
return;
}
#endif
if (m==1) {
do{
*Fout = *f;
f += fstride*in_stride;
}while(++Fout != Fout_end );
}else{
do{
// recursive call:
// DFT of size m*p performed by doing
// p instances of smaller DFTs of size m,
// each one takes a decimated version of the input
kf_work( Fout , f, fstride*p, in_stride, factors,st);
f += fstride*in_stride;
}while( (Fout += m) != Fout_end );
}
Fout=Fout_beg;
// recombine the p smaller DFTs
switch (p) {
case 2: kf_bfly2(Fout,fstride,st,m); break;
case 3: kf_bfly3(Fout,fstride,st,m); break;
case 4: kf_bfly4(Fout,fstride,st,m); break;
case 5: kf_bfly5(Fout,fstride,st,m); break;
default: kf_bfly_generic(Fout,fstride,st,m,p); break;
}
}
/* facbuf is populated by p1,m1,p2,m2, ...
where
p[i] * m[i] = m[i-1]
m0 = n */
static
void kf_factor(int n,int * facbuf)
{
int p=4;
double floor_sqrt;
floor_sqrt = floor( sqrt((double)n) );
/*factor out powers of 4, powers of 2, then any remaining primes */
do {
while (n % p) {
switch (p) {
case 4: p = 2; break;
case 2: p = 3; break;
default: p += 2; break;
}
if (p > floor_sqrt)
p = n; /* no more factors, skip to end */
}
n /= p;
*facbuf++ = p;
*facbuf++ = n;
} while (n > 1);
}
/*
*
* User-callable function to allocate all necessary storage space for the fft.
*
* The return value is a contiguous block of memory, allocated with malloc. As such,
* It can be freed with free(), rather than a kiss_fft-specific function.
* */
kiss_fft_cfg kiss_fft_alloc(int nfft,int inverse_fft,void * mem,size_t * lenmem )
{
kiss_fft_cfg st=NULL;
size_t memneeded = sizeof(struct kiss_fft_state)
+ sizeof(kiss_fft_cpx)*(nfft-1); /* twiddle factors*/
if ( lenmem==NULL ) {
st = ( kiss_fft_cfg)KISS_FFT_MALLOC( memneeded );
}else{
if (mem != NULL && *lenmem >= memneeded)
st = (kiss_fft_cfg)mem;
*lenmem = memneeded;
}
if (st) {
int i;
st->nfft=nfft;
st->inverse = inverse_fft;
for (i=0;i<nfft;++i) {
const double pi=3.141592653589793238462643383279502884197169399375105820974944;
double phase = -2*pi*i / nfft;
if (st->inverse)
phase *= -1;
kf_cexp(st->twiddles+i, phase );
}
kf_factor(nfft,st->factors);
}
return st;
}
void kiss_fft_stride(kiss_fft_cfg st,const kiss_fft_cpx *fin,kiss_fft_cpx *fout,int in_stride)
{
if (fin == fout) {
//NOTE: this is not really an in-place FFT algorithm.
//It just performs an out-of-place FFT into a temp buffer
kiss_fft_cpx * tmpbuf = (kiss_fft_cpx*)KISS_FFT_TMP_ALLOC( sizeof(kiss_fft_cpx)*st->nfft);
kf_work(tmpbuf,fin,1,in_stride, st->factors,st);
memcpy(fout,tmpbuf,sizeof(kiss_fft_cpx)*st->nfft);
KISS_FFT_TMP_FREE(tmpbuf);
}else{
kf_work( fout, fin, 1,in_stride, st->factors,st );
}
}
void kiss_fft(kiss_fft_cfg cfg,const kiss_fft_cpx *fin,kiss_fft_cpx *fout)
{
kiss_fft_stride(cfg,fin,fout,1);
}
void kiss_fft_cleanup(void)
{
// nothing needed any more
}
int kiss_fft_next_fast_size(int n)
{
while(1) {
int m=n;
while ( (m%2) == 0 ) m/=2;
while ( (m%3) == 0 ) m/=3;
while ( (m%5) == 0 ) m/=5;
if (m<=1)
break; /* n is completely factorable by twos, threes, and fives */
n++;
}
return n;
}

View File

@ -1,125 +0,0 @@
#ifndef KISS_FFT_H
#define KISS_FFT_H
#include <stdlib.h>
#include <stdio.h>
#include <math.h>
#include <string.h>
#include <malloc.h>
#ifdef __cplusplus
extern "C" {
#endif
/*
ATTENTION!
If you would like a :
-- a utility that will handle the caching of fft objects
-- real-only (no imaginary time component ) FFT
-- a multi-dimensional FFT
-- a command-line utility to perform ffts
-- a command-line utility to perform fast-convolution filtering
Then see kfc.h kiss_fftr.h kiss_fftnd.h fftutil.c kiss_fastfir.c
in the tools/ directory.
*/
#ifdef USE_SIMD
# include <xmmintrin.h>
# define kiss_fft_scalar __m128
#define KISS_FFT_MALLOC(nbytes) _mm_malloc(nbytes,16)
#define KISS_FFT_FREE _mm_free
#else
#define KISS_FFT_MALLOC malloc
#define KISS_FFT_FREE free
#endif
#ifdef FIXED_POINT
#include <sys/types.h>
# if (FIXED_POINT == 32)
# define kiss_fft_scalar int32_t
# else
# define kiss_fft_scalar int16_t
# endif
#else
# ifndef kiss_fft_scalar
/* default is float */
# define kiss_fft_scalar float
# endif
#endif
typedef struct {
kiss_fft_scalar r;
kiss_fft_scalar i;
}kiss_fft_cpx;
typedef struct kiss_fft_state* kiss_fft_cfg;
/*
* kiss_fft_alloc
*
* Initialize a FFT (or IFFT) algorithm's cfg/state buffer.
*
* typical usage: kiss_fft_cfg mycfg=kiss_fft_alloc(1024,0,NULL,NULL);
*
* The return value from fft_alloc is a cfg buffer used internally
* by the fft routine or NULL.
*
* If lenmem is NULL, then kiss_fft_alloc will allocate a cfg buffer using malloc.
* The returned value should be free()d when done to avoid memory leaks.
*
* The state can be placed in a user supplied buffer 'mem':
* If lenmem is not NULL and mem is not NULL and *lenmem is large enough,
* then the function places the cfg in mem and the size used in *lenmem
* and returns mem.
*
* If lenmem is not NULL and ( mem is NULL or *lenmem is not large enough),
* then the function returns NULL and places the minimum cfg
* buffer size in *lenmem.
* */
kiss_fft_cfg kiss_fft_alloc(int nfft,int inverse_fft,void * mem,size_t * lenmem);
/*
* kiss_fft(cfg,in_out_buf)
*
* Perform an FFT on a complex input buffer.
* for a forward FFT,
* fin should be f[0] , f[1] , ... ,f[nfft-1]
* fout will be F[0] , F[1] , ... ,F[nfft-1]
* Note that each element is complex and can be accessed like
f[k].r and f[k].i
* */
void kiss_fft(kiss_fft_cfg cfg,const kiss_fft_cpx *fin,kiss_fft_cpx *fout);
/*
A more generic version of the above function. It reads its input from every Nth sample.
* */
void kiss_fft_stride(kiss_fft_cfg cfg,const kiss_fft_cpx *fin,kiss_fft_cpx *fout,int fin_stride);
/* If kiss_fft_alloc allocated a buffer, it is one contiguous
buffer and can be simply free()d when no longer needed*/
#define kiss_fft_free free
/*
Cleans up some memory that gets managed internally. Not necessary to call, but it might clean up
your compiler output to call this before you exit.
*/
void kiss_fft_cleanup(void);
/*
* Returns the smallest integer k, such that k>=n and k has only "fast" factors (2,3,5)
*/
int kiss_fft_next_fast_size(int n);
/* for real ffts, we need an even size */
#define kiss_fftr_next_fast_size_real(n) \
(kiss_fft_next_fast_size( ((n)+1)>>1)<<1)
#ifdef __cplusplus
}
#endif
#endif

View File

@ -1,11 +0,0 @@
Copyright (c) 2003-2010 Mark Borgerding
All rights reserved.
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
* Neither the author nor the names of any contributors may be used to endorse or promote products derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

File diff suppressed because it is too large Load Diff

View File

@ -1,162 +0,0 @@
#ifndef WAVELET2D_H
#define WAVELET2D_H
#include <vector>
#include <complex>
using namespace std;
// the dll exports
#if defined WAVE_EXPORT
#define EXPORT __declspec(dllexport)
#else
#define EXPORT __declspec(dllimport)
#endif
// 1D Functions
EXPORT void* dwt1(string, vector<double> &, vector<double> &, vector<double> &);
EXPORT void* dyadic_zpad_1d(vector<double> &);
EXPORT double convol(vector<double> &, vector<double> &, vector<double> &);
EXPORT int filtcoef(string , vector<double> &, vector<double> &, vector<double> &,
vector<double> &);
EXPORT void downsamp(vector<double> &, int , vector<double> &);
EXPORT void upsamp(vector<double> &, int, vector<double> &);
EXPORT void circshift(vector<double> &, int );
EXPORT int sign(int);
EXPORT void* idwt1(string wname, vector<double> &, vector<double> &, vector<double> &);
EXPORT int vecsum(vector<double> &, vector<double> &, vector<double> &);
// 1D Symmetric Extension DWT Functions
EXPORT void* dwt_sym(vector<double> &, int ,string , vector<double> &,vector<double> &,
vector<int> &);
EXPORT void* dwt1_sym(string , vector<double> &, vector<double> &, vector<double> &);
EXPORT void* idwt_sym(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
EXPORT void* symm_ext(vector<double> &, int );
EXPORT void* idwt1_sym(string, vector<double> &, vector<double> &, vector<double> &); // Not Tested
// 1D Stationary Wavelet Transform
EXPORT void* swt(vector<double> &, int , string , vector<double> &, int &) ;
EXPORT void* iswt(vector<double> &,int , string, vector<double> &);
EXPORT void* per_ext(vector<double> &, int );
// 2D Functions
EXPORT void* branch_lp_dn(string , vector<double> &, vector<double> &);
EXPORT void* branch_hp_dn(string , vector<double> &, vector<double> &);
EXPORT void* branch_lp_hp_up(string ,vector<double> &, vector<double> &, vector<double> &);
//EXPORT void* dwt_2d(vector<vector<double> > &, int , string , vector<vector<double> > &
// , vector<double> &) ;
//EXPORT void* idwt_2d(vector<vector<double> > &,vector<double> &, string ,vector<vector<double> > &);
EXPORT void* dyadic_zpad_2d(vector<vector<double> > &,vector<vector<double> > &);
EXPORT void* dwt_output_dim(vector<vector<double> >&, int &, int & );
EXPORT void* zero_remove(vector<vector<double> > &,vector<vector<double> > &) ;
EXPORT void* getcoeff2d(vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &,vector<vector<double> > &,vector<double> &, int &);
EXPORT void* idwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* dwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* downsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
EXPORT void* upsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
// 2D DWT (Symmetric Extension) Functions
EXPORT void* dwt_2d_sym(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
EXPORT void* dwt2_sym(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* idwt_2d_sym(vector<double> &,vector<double> &, string ,vector<vector<double> > &,
vector<int> &);
EXPORT void* circshift2d(vector<vector<double> > &, int , int );
EXPORT void symm_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
EXPORT void* dispDWT(vector<double> &,vector<vector<double> > &, vector<int> &, vector<int> &, int ) ;
EXPORT void* dwt_output_dim_sym(vector<int> &,vector<int> &, int );
//2D Stationary Wavelet Transform
EXPORT void* swt_2d(vector<vector<double> > &,int , string , vector<double> &);
EXPORT void* per_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
// FFT functions
EXPORT double convfft(vector<double> &, vector<double> &, vector<double> &);
EXPORT double convfftm(vector<double> &, vector<double> &, vector<double> &);
EXPORT void* fft(vector<complex<double> > &,int ,unsigned int);
EXPORT void* bitreverse(vector<complex<double> > &);
EXPORT void* freq(vector<double> &, vector<double> &);
//New
EXPORT void* dwt1_sym_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD);//FFTW3 for 2D
EXPORT void* idwt1_sym_m(string wname, vector<double> &X, vector<double> &app, vector<double> &detail);
EXPORT void* dwt(vector<double> &sig, int J, string nm, vector<double> &dwt_output
, vector<double> &flag, vector<int> &length );
EXPORT void* idwt(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
EXPORT void* dwt_2d(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
EXPORT void* dwt1_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD) ;
EXPORT void* idwt_2d(vector<double> &dwtop,vector<double> &flag, string nm,
vector<vector<double> > &idwt_output, vector<int> &length);
EXPORT void* idwt1_m(string wname, vector<double> &X, vector<double> &cA, vector<double> &cD);
EXPORT void* dwt_output_dim2(vector<int> &length, vector<int> &length2, int J);
#endif/* WAVELET2D_H */

View File

@ -1,340 +0,0 @@
GNU GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1989, 1991 Free Software Foundation, Inc.
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. This
General Public License applies to most of the Free Software
Foundation's software and to any other program whose authors commit to
using it. (Some other Free Software Foundation software is covered by
the GNU Library General Public License instead.) You can apply it to
your programs, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must show them these terms so they know their
rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that redistributors of a free
program will individually obtain patent licenses, in effect making the
program proprietary. To prevent this, we have made it clear that any
patent must be licensed for everyone's free use or not licensed at all.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License applies to any program or other work which contains
a notice placed by the copyright holder saying it may be distributed
under the terms of this General Public License. The "Program", below,
refers to any such program or work, and a "work based on the Program"
means either the Program or any derivative work under copyright law:
that is to say, a work containing the Program or a portion of it,
either verbatim or with modifications and/or translated into another
language. (Hereinafter, translation is included without limitation in
the term "modification".) Each licensee is addressed as "you".
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running the Program is not restricted, and the output from the Program
is covered only if its contents constitute a work based on the
Program (independent of having been made by running the Program).
Whether that is true depends on what the Program does.
1. You may copy and distribute verbatim copies of the Program's
source code as you receive it, in any medium, provided that you
conspicuously and appropriately publish on each copy an appropriate
copyright notice and disclaimer of warranty; keep intact all the
notices that refer to this License and to the absence of any warranty;
and give any other recipients of the Program a copy of this License
along with the Program.
You may charge a fee for the physical act of transferring a copy, and
you may at your option offer warranty protection in exchange for a fee.
2. You may modify your copy or copies of the Program or any portion
of it, thus forming a work based on the Program, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) You must cause the modified files to carry prominent notices
stating that you changed the files and the date of any change.
b) You must cause any work that you distribute or publish, that in
whole or in part contains or is derived from the Program or any
part thereof, to be licensed as a whole at no charge to all third
parties under the terms of this License.
c) If the modified program normally reads commands interactively
when run, you must cause it, when started running for such
interactive use in the most ordinary way, to print or display an
announcement including an appropriate copyright notice and a
notice that there is no warranty (or else, saying that you provide
a warranty) and that users may redistribute the program under
these conditions, and telling the user how to view a copy of this
License. (Exception: if the Program itself is interactive but
does not normally print such an announcement, your work based on
the Program is not required to print an announcement.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Program,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Program, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Program.
In addition, mere aggregation of another work not based on the Program
with the Program (or with a work based on the Program) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may copy and distribute the Program (or a work based on it,
under Section 2) in object code or executable form under the terms of
Sections 1 and 2 above provided that you also do one of the following:
a) Accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of Sections
1 and 2 above on a medium customarily used for software interchange; or,
b) Accompany it with a written offer, valid for at least three
years, to give any third party, for a charge no more than your
cost of physically performing source distribution, a complete
machine-readable copy of the corresponding source code, to be
distributed under the terms of Sections 1 and 2 above on a medium
customarily used for software interchange; or,
c) Accompany it with the information you received as to the offer
to distribute corresponding source code. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form with such
an offer, in accord with Subsection b above.)
The source code for a work means the preferred form of the work for
making modifications to it. For an executable work, complete source
code means all the source code for all modules it contains, plus any
associated interface definition files, plus the scripts used to
control compilation and installation of the executable. However, as a
special exception, the source code distributed need not include
anything that is normally distributed (in either source or binary
form) with the major components (compiler, kernel, and so on) of the
operating system on which the executable runs, unless that component
itself accompanies the executable.
If distribution of executable or object code is made by offering
access to copy from a designated place, then offering equivalent
access to copy the source code from the same place counts as
distribution of the source code, even though third parties are not
compelled to copy the source along with the object code.
4. You may not copy, modify, sublicense, or distribute the Program
except as expressly provided under this License. Any attempt
otherwise to copy, modify, sublicense or distribute the Program is
void, and will automatically terminate your rights under this License.
However, parties who have received copies, or rights, from you under
this License will not have their licenses terminated so long as such
parties remain in full compliance.
5. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Program or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Program (or any work based on the
Program), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Program or works based on it.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the
original licensor to copy, distribute or modify the Program subject to
these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
7. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Program at all. For example, if a patent
license would not permit royalty-free redistribution of the Program by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Program.
If any portion of this section is held invalid or unenforceable under
any particular circumstance, the balance of the section is intended to
apply and the section as a whole is intended to apply in other
circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system, which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
8. If the distribution and/or use of the Program is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Program under this License
may add an explicit geographical distribution limitation excluding
those countries, so that distribution is permitted only in or among
countries not thus excluded. In such case, this License incorporates
the limitation as if written in the body of this License.
9. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of this License which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
this License, you may choose any version ever published by the Free Software
Foundation.
10. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to the public, the best way to achieve this is to make it
free software which everyone can redistribute and change under these terms.
To do so, attach the following notices to the program. It is safest
to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least
the "copyright" line and a pointer to where the full notice is found.
<one line to give the program's name and a brief idea of what it does.>
Copyright (C) <year> <name of author>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Also add information on how to contact you by electronic and paper mail.
If the program is interactive, make it output a short notice like this
when it starts in an interactive mode:
Gnomovision version 69, Copyright (C) year name of author
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the appropriate
parts of the General Public License. Of course, the commands you use may
be called something other than `show w' and `show c'; they could even be
mouse-clicks or menu items--whatever suits your program.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the program, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
`Gnomovision' (which makes passes at compilers) written by James Hacker.
<signature of Ty Coon>, 1 April 1989
Ty Coon, President of Vice
This General Public License does not permit incorporating your program into
proprietary programs. If your program is a subroutine library, you may
consider it more useful to permit linking proprietary applications with the
library. If this is what you want to do, use the GNU Library General
Public License instead of this License.

View File

@ -1,21 +0,0 @@
/*
* Copyright (c) 2011 Rafat Hussain
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.This program also uses FFTW3 library
* for high speed computation and it is being distributed in accordance
* with GNU-GPL license ver 2.0
* For FFTW3 copyright information, see the FFTW3 folder.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
*/

View File

@ -1,164 +0,0 @@
/*
Copyright (c) 2003-2010, Mark Borgerding
All rights reserved.
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
* Neither the author nor the names of any contributors may be used to endorse or promote products derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/* kiss_fft.h
defines kiss_fft_scalar as either short or a float type
and defines
typedef struct { kiss_fft_scalar r; kiss_fft_scalar i; }kiss_fft_cpx; */
#include "kiss_fft.h"
#include <limits.h>
#define MAXFACTORS 32
/* e.g. an fft of length 128 has 4 factors
as far as kissfft is concerned
4*4*4*2
*/
struct kiss_fft_state{
int nfft;
int inverse;
int factors[2*MAXFACTORS];
kiss_fft_cpx twiddles[1];
};
/*
Explanation of macros dealing with complex math:
C_MUL(m,a,b) : m = a*b
C_FIXDIV( c , div ) : if a fixed point impl., c /= div. noop otherwise
C_SUB( res, a,b) : res = a - b
C_SUBFROM( res , a) : res -= a
C_ADDTO( res , a) : res += a
* */
#ifdef FIXED_POINT
#if (FIXED_POINT==32)
# define FRACBITS 31
# define SAMPPROD int64_t
#define SAMP_MAX 2147483647
#else
# define FRACBITS 15
# define SAMPPROD int32_t
#define SAMP_MAX 32767
#endif
#define SAMP_MIN -SAMP_MAX
#if defined(CHECK_OVERFLOW)
# define CHECK_OVERFLOW_OP(a,op,b) \
if ( (SAMPPROD)(a) op (SAMPPROD)(b) > SAMP_MAX || (SAMPPROD)(a) op (SAMPPROD)(b) < SAMP_MIN ) { \
fprintf(stderr,"WARNING:overflow @ " __FILE__ "(%d): (%d " #op" %d) = %ld\n",__LINE__,(a),(b),(SAMPPROD)(a) op (SAMPPROD)(b) ); }
#endif
# define smul(a,b) ( (SAMPPROD)(a)*(b) )
# define sround( x ) (kiss_fft_scalar)( ( (x) + (1<<(FRACBITS-1)) ) >> FRACBITS )
# define S_MUL(a,b) sround( smul(a,b) )
# define C_MUL(m,a,b) \
do{ (m).r = sround( smul((a).r,(b).r) - smul((a).i,(b).i) ); \
(m).i = sround( smul((a).r,(b).i) + smul((a).i,(b).r) ); }while(0)
# define DIVSCALAR(x,k) \
(x) = sround( smul( x, SAMP_MAX/k ) )
# define C_FIXDIV(c,div) \
do { DIVSCALAR( (c).r , div); \
DIVSCALAR( (c).i , div); }while (0)
# define C_MULBYSCALAR( c, s ) \
do{ (c).r = sround( smul( (c).r , s ) ) ;\
(c).i = sround( smul( (c).i , s ) ) ; }while(0)
#else /* not FIXED_POINT*/
# define S_MUL(a,b) ( (a)*(b) )
#define C_MUL(m,a,b) \
do{ (m).r = (a).r*(b).r - (a).i*(b).i;\
(m).i = (a).r*(b).i + (a).i*(b).r; }while(0)
# define C_FIXDIV(c,div) /* NOOP */
# define C_MULBYSCALAR( c, s ) \
do{ (c).r *= (s);\
(c).i *= (s); }while(0)
#endif
#ifndef CHECK_OVERFLOW_OP
# define CHECK_OVERFLOW_OP(a,op,b) /* noop */
#endif
#define C_ADD( res, a,b)\
do { \
CHECK_OVERFLOW_OP((a).r,+,(b).r)\
CHECK_OVERFLOW_OP((a).i,+,(b).i)\
(res).r=(a).r+(b).r; (res).i=(a).i+(b).i; \
}while(0)
#define C_SUB( res, a,b)\
do { \
CHECK_OVERFLOW_OP((a).r,-,(b).r)\
CHECK_OVERFLOW_OP((a).i,-,(b).i)\
(res).r=(a).r-(b).r; (res).i=(a).i-(b).i; \
}while(0)
#define C_ADDTO( res , a)\
do { \
CHECK_OVERFLOW_OP((res).r,+,(a).r)\
CHECK_OVERFLOW_OP((res).i,+,(a).i)\
(res).r += (a).r; (res).i += (a).i;\
}while(0)
#define C_SUBFROM( res , a)\
do {\
CHECK_OVERFLOW_OP((res).r,-,(a).r)\
CHECK_OVERFLOW_OP((res).i,-,(a).i)\
(res).r -= (a).r; (res).i -= (a).i; \
}while(0)
#ifdef FIXED_POINT
# define KISS_FFT_COS(phase) floor(.5+SAMP_MAX * cos (phase))
# define KISS_FFT_SIN(phase) floor(.5+SAMP_MAX * sin (phase))
# define HALF_OF(x) ((x)>>1)
#elif defined(USE_SIMD)
# define KISS_FFT_COS(phase) _mm_set1_ps( cos(phase) )
# define KISS_FFT_SIN(phase) _mm_set1_ps( sin(phase) )
# define HALF_OF(x) ((x)*_mm_set1_ps(.5))
#else
# define KISS_FFT_COS(phase) (kiss_fft_scalar) cos(phase)
# define KISS_FFT_SIN(phase) (kiss_fft_scalar) sin(phase)
# define HALF_OF(x) ((x)*.5)
#endif
#define kf_cexp(x,phase) \
do{ \
(x)->r = KISS_FFT_COS(phase);\
(x)->i = KISS_FFT_SIN(phase);\
}while(0)
/* a debugging function */
#define pcpx(c)\
fprintf(stderr,"%g + %gi\n",(double)((c)->r),(double)((c)->i) )
#ifdef KISS_FFT_USE_ALLOCA
// define this to allow use of alloca instead of malloc for temporary buffers
// Temporary buffers are used in two case:
// 1. FFT sizes that have "bad" factors. i.e. not 2,3 and 5
// 2. "in-place" FFTs. Notice the quotes, since kissfft does not really do an in-place transform.
#include <alloca.h>
#define KISS_FFT_TMP_ALLOC(nbytes) alloca(nbytes)
#define KISS_FFT_TMP_FREE(ptr)
#else
#define KISS_FFT_TMP_ALLOC(nbytes) KISS_FFT_MALLOC(nbytes)
#define KISS_FFT_TMP_FREE(ptr) KISS_FFT_FREE(ptr)
#endif

View File

@ -1,408 +0,0 @@
/*
Copyright (c) 2003-2010, Mark Borgerding
All rights reserved.
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
* Neither the author nor the names of any contributors may be used to endorse or promote products derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "_kiss_fft_guts.h"
/* The guts header contains all the multiplication and addition macros that are defined for
fixed or floating point complex numbers. It also delares the kf_ internal functions.
*/
static void kf_bfly2(
kiss_fft_cpx * Fout,
const size_t fstride,
const kiss_fft_cfg st,
int m
)
{
kiss_fft_cpx * Fout2;
kiss_fft_cpx * tw1 = st->twiddles;
kiss_fft_cpx t;
Fout2 = Fout + m;
do{
C_FIXDIV(*Fout,2); C_FIXDIV(*Fout2,2);
C_MUL (t, *Fout2 , *tw1);
tw1 += fstride;
C_SUB( *Fout2 , *Fout , t );
C_ADDTO( *Fout , t );
++Fout2;
++Fout;
}while (--m);
}
static void kf_bfly4(
kiss_fft_cpx * Fout,
const size_t fstride,
const kiss_fft_cfg st,
const size_t m
)
{
kiss_fft_cpx *tw1,*tw2,*tw3;
kiss_fft_cpx scratch[6];
size_t k=m;
const size_t m2=2*m;
const size_t m3=3*m;
tw3 = tw2 = tw1 = st->twiddles;
do {
C_FIXDIV(*Fout,4); C_FIXDIV(Fout[m],4); C_FIXDIV(Fout[m2],4); C_FIXDIV(Fout[m3],4);
C_MUL(scratch[0],Fout[m] , *tw1 );
C_MUL(scratch[1],Fout[m2] , *tw2 );
C_MUL(scratch[2],Fout[m3] , *tw3 );
C_SUB( scratch[5] , *Fout, scratch[1] );
C_ADDTO(*Fout, scratch[1]);
C_ADD( scratch[3] , scratch[0] , scratch[2] );
C_SUB( scratch[4] , scratch[0] , scratch[2] );
C_SUB( Fout[m2], *Fout, scratch[3] );
tw1 += fstride;
tw2 += fstride*2;
tw3 += fstride*3;
C_ADDTO( *Fout , scratch[3] );
if(st->inverse) {
Fout[m].r = scratch[5].r - scratch[4].i;
Fout[m].i = scratch[5].i + scratch[4].r;
Fout[m3].r = scratch[5].r + scratch[4].i;
Fout[m3].i = scratch[5].i - scratch[4].r;
}else{
Fout[m].r = scratch[5].r + scratch[4].i;
Fout[m].i = scratch[5].i - scratch[4].r;
Fout[m3].r = scratch[5].r - scratch[4].i;
Fout[m3].i = scratch[5].i + scratch[4].r;
}
++Fout;
}while(--k);
}
static void kf_bfly3(
kiss_fft_cpx * Fout,
const size_t fstride,
const kiss_fft_cfg st,
size_t m
)
{
size_t k=m;
const size_t m2 = 2*m;
kiss_fft_cpx *tw1,*tw2;
kiss_fft_cpx scratch[5];
kiss_fft_cpx epi3;
epi3 = st->twiddles[fstride*m];
tw1=tw2=st->twiddles;
do{
C_FIXDIV(*Fout,3); C_FIXDIV(Fout[m],3); C_FIXDIV(Fout[m2],3);
C_MUL(scratch[1],Fout[m] , *tw1);
C_MUL(scratch[2],Fout[m2] , *tw2);
C_ADD(scratch[3],scratch[1],scratch[2]);
C_SUB(scratch[0],scratch[1],scratch[2]);
tw1 += fstride;
tw2 += fstride*2;
Fout[m].r = Fout->r - HALF_OF(scratch[3].r);
Fout[m].i = Fout->i - HALF_OF(scratch[3].i);
C_MULBYSCALAR( scratch[0] , epi3.i );
C_ADDTO(*Fout,scratch[3]);
Fout[m2].r = Fout[m].r + scratch[0].i;
Fout[m2].i = Fout[m].i - scratch[0].r;
Fout[m].r -= scratch[0].i;
Fout[m].i += scratch[0].r;
++Fout;
}while(--k);
}
static void kf_bfly5(
kiss_fft_cpx * Fout,
const size_t fstride,
const kiss_fft_cfg st,
int m
)
{
kiss_fft_cpx *Fout0,*Fout1,*Fout2,*Fout3,*Fout4;
int u;
kiss_fft_cpx scratch[13];
kiss_fft_cpx * twiddles = st->twiddles;
kiss_fft_cpx *tw;
kiss_fft_cpx ya,yb;
ya = twiddles[fstride*m];
yb = twiddles[fstride*2*m];
Fout0=Fout;
Fout1=Fout0+m;
Fout2=Fout0+2*m;
Fout3=Fout0+3*m;
Fout4=Fout0+4*m;
tw=st->twiddles;
for ( u=0; u<m; ++u ) {
C_FIXDIV( *Fout0,5); C_FIXDIV( *Fout1,5); C_FIXDIV( *Fout2,5); C_FIXDIV( *Fout3,5); C_FIXDIV( *Fout4,5);
scratch[0] = *Fout0;
C_MUL(scratch[1] ,*Fout1, tw[u*fstride]);
C_MUL(scratch[2] ,*Fout2, tw[2*u*fstride]);
C_MUL(scratch[3] ,*Fout3, tw[3*u*fstride]);
C_MUL(scratch[4] ,*Fout4, tw[4*u*fstride]);
C_ADD( scratch[7],scratch[1],scratch[4]);
C_SUB( scratch[10],scratch[1],scratch[4]);
C_ADD( scratch[8],scratch[2],scratch[3]);
C_SUB( scratch[9],scratch[2],scratch[3]);
Fout0->r += scratch[7].r + scratch[8].r;
Fout0->i += scratch[7].i + scratch[8].i;
scratch[5].r = scratch[0].r + S_MUL(scratch[7].r,ya.r) + S_MUL(scratch[8].r,yb.r);
scratch[5].i = scratch[0].i + S_MUL(scratch[7].i,ya.r) + S_MUL(scratch[8].i,yb.r);
scratch[6].r = S_MUL(scratch[10].i,ya.i) + S_MUL(scratch[9].i,yb.i);
scratch[6].i = -S_MUL(scratch[10].r,ya.i) - S_MUL(scratch[9].r,yb.i);
C_SUB(*Fout1,scratch[5],scratch[6]);
C_ADD(*Fout4,scratch[5],scratch[6]);
scratch[11].r = scratch[0].r + S_MUL(scratch[7].r,yb.r) + S_MUL(scratch[8].r,ya.r);
scratch[11].i = scratch[0].i + S_MUL(scratch[7].i,yb.r) + S_MUL(scratch[8].i,ya.r);
scratch[12].r = - S_MUL(scratch[10].i,yb.i) + S_MUL(scratch[9].i,ya.i);
scratch[12].i = S_MUL(scratch[10].r,yb.i) - S_MUL(scratch[9].r,ya.i);
C_ADD(*Fout2,scratch[11],scratch[12]);
C_SUB(*Fout3,scratch[11],scratch[12]);
++Fout0;++Fout1;++Fout2;++Fout3;++Fout4;
}
}
/* perform the butterfly for one stage of a mixed radix FFT */
static void kf_bfly_generic(
kiss_fft_cpx * Fout,
const size_t fstride,
const kiss_fft_cfg st,
int m,
int p
)
{
int u,k,q1,q;
kiss_fft_cpx * twiddles = st->twiddles;
kiss_fft_cpx t;
int Norig = st->nfft;
kiss_fft_cpx * scratch = (kiss_fft_cpx*)KISS_FFT_TMP_ALLOC(sizeof(kiss_fft_cpx)*p);
for ( u=0; u<m; ++u ) {
k=u;
for ( q1=0 ; q1<p ; ++q1 ) {
scratch[q1] = Fout[ k ];
C_FIXDIV(scratch[q1],p);
k += m;
}
k=u;
for ( q1=0 ; q1<p ; ++q1 ) {
int twidx=0;
Fout[ k ] = scratch[0];
for (q=1;q<p;++q ) {
twidx += fstride * k;
if (twidx>=Norig) twidx-=Norig;
C_MUL(t,scratch[q] , twiddles[twidx] );
C_ADDTO( Fout[ k ] ,t);
}
k += m;
}
}
KISS_FFT_TMP_FREE(scratch);
}
static
void kf_work(
kiss_fft_cpx * Fout,
const kiss_fft_cpx * f,
const size_t fstride,
int in_stride,
int * factors,
const kiss_fft_cfg st
)
{
kiss_fft_cpx * Fout_beg=Fout;
const int p=*factors++; /* the radix */
const int m=*factors++; /* stage's fft length/p */
const kiss_fft_cpx * Fout_end = Fout + p*m;
#ifdef _OPENMP
// use openmp extensions at the
// top-level (not recursive)
if (fstride==1 && p<=5)
{
int k;
// execute the p different work units in different threads
# pragma omp parallel for
for (k=0;k<p;++k)
kf_work( Fout +k*m, f+ fstride*in_stride*k,fstride*p,in_stride,factors,st);
// all threads have joined by this point
switch (p) {
case 2: kf_bfly2(Fout,fstride,st,m); break;
case 3: kf_bfly3(Fout,fstride,st,m); break;
case 4: kf_bfly4(Fout,fstride,st,m); break;
case 5: kf_bfly5(Fout,fstride,st,m); break;
default: kf_bfly_generic(Fout,fstride,st,m,p); break;
}
return;
}
#endif
if (m==1) {
do{
*Fout = *f;
f += fstride*in_stride;
}while(++Fout != Fout_end );
}else{
do{
// recursive call:
// DFT of size m*p performed by doing
// p instances of smaller DFTs of size m,
// each one takes a decimated version of the input
kf_work( Fout , f, fstride*p, in_stride, factors,st);
f += fstride*in_stride;
}while( (Fout += m) != Fout_end );
}
Fout=Fout_beg;
// recombine the p smaller DFTs
switch (p) {
case 2: kf_bfly2(Fout,fstride,st,m); break;
case 3: kf_bfly3(Fout,fstride,st,m); break;
case 4: kf_bfly4(Fout,fstride,st,m); break;
case 5: kf_bfly5(Fout,fstride,st,m); break;
default: kf_bfly_generic(Fout,fstride,st,m,p); break;
}
}
/* facbuf is populated by p1,m1,p2,m2, ...
where
p[i] * m[i] = m[i-1]
m0 = n */
static
void kf_factor(int n,int * facbuf)
{
int p=4;
double floor_sqrt;
floor_sqrt = floor( sqrt((double)n) );
/*factor out powers of 4, powers of 2, then any remaining primes */
do {
while (n % p) {
switch (p) {
case 4: p = 2; break;
case 2: p = 3; break;
default: p += 2; break;
}
if (p > floor_sqrt)
p = n; /* no more factors, skip to end */
}
n /= p;
*facbuf++ = p;
*facbuf++ = n;
} while (n > 1);
}
/*
*
* User-callable function to allocate all necessary storage space for the fft.
*
* The return value is a contiguous block of memory, allocated with malloc. As such,
* It can be freed with free(), rather than a kiss_fft-specific function.
* */
kiss_fft_cfg kiss_fft_alloc(int nfft,int inverse_fft,void * mem,size_t * lenmem )
{
kiss_fft_cfg st=NULL;
size_t memneeded = sizeof(struct kiss_fft_state)
+ sizeof(kiss_fft_cpx)*(nfft-1); /* twiddle factors*/
if ( lenmem==NULL ) {
st = ( kiss_fft_cfg)KISS_FFT_MALLOC( memneeded );
}else{
if (mem != NULL && *lenmem >= memneeded)
st = (kiss_fft_cfg)mem;
*lenmem = memneeded;
}
if (st) {
int i;
st->nfft=nfft;
st->inverse = inverse_fft;
for (i=0;i<nfft;++i) {
const double pi=3.141592653589793238462643383279502884197169399375105820974944;
double phase = -2*pi*i / nfft;
if (st->inverse)
phase *= -1;
kf_cexp(st->twiddles+i, phase );
}
kf_factor(nfft,st->factors);
}
return st;
}
void kiss_fft_stride(kiss_fft_cfg st,const kiss_fft_cpx *fin,kiss_fft_cpx *fout,int in_stride)
{
if (fin == fout) {
//NOTE: this is not really an in-place FFT algorithm.
//It just performs an out-of-place FFT into a temp buffer
kiss_fft_cpx * tmpbuf = (kiss_fft_cpx*)KISS_FFT_TMP_ALLOC( sizeof(kiss_fft_cpx)*st->nfft);
kf_work(tmpbuf,fin,1,in_stride, st->factors,st);
memcpy(fout,tmpbuf,sizeof(kiss_fft_cpx)*st->nfft);
KISS_FFT_TMP_FREE(tmpbuf);
}else{
kf_work( fout, fin, 1,in_stride, st->factors,st );
}
}
void kiss_fft(kiss_fft_cfg cfg,const kiss_fft_cpx *fin,kiss_fft_cpx *fout)
{
kiss_fft_stride(cfg,fin,fout,1);
}
void kiss_fft_cleanup(void)
{
// nothing needed any more
}
int kiss_fft_next_fast_size(int n)
{
while(1) {
int m=n;
while ( (m%2) == 0 ) m/=2;
while ( (m%3) == 0 ) m/=3;
while ( (m%5) == 0 ) m/=5;
if (m<=1)
break; /* n is completely factorable by twos, threes, and fives */
n++;
}
return n;
}

View File

@ -1,125 +0,0 @@
#ifndef KISS_FFT_H
#define KISS_FFT_H
#include <stdlib.h>
#include <stdio.h>
#include <math.h>
#include <string.h>
#include <malloc.h>
#ifdef __cplusplus
extern "C" {
#endif
/*
ATTENTION!
If you would like a :
-- a utility that will handle the caching of fft objects
-- real-only (no imaginary time component ) FFT
-- a multi-dimensional FFT
-- a command-line utility to perform ffts
-- a command-line utility to perform fast-convolution filtering
Then see kfc.h kiss_fftr.h kiss_fftnd.h fftutil.c kiss_fastfir.c
in the tools/ directory.
*/
#ifdef USE_SIMD
# include <xmmintrin.h>
# define kiss_fft_scalar __m128
#define KISS_FFT_MALLOC(nbytes) _mm_malloc(nbytes,16)
#define KISS_FFT_FREE _mm_free
#else
#define KISS_FFT_MALLOC malloc
#define KISS_FFT_FREE free
#endif
#ifdef FIXED_POINT
#include <sys/types.h>
# if (FIXED_POINT == 32)
# define kiss_fft_scalar int32_t
# else
# define kiss_fft_scalar int16_t
# endif
#else
# ifndef kiss_fft_scalar
/* default is float */
# define kiss_fft_scalar float
# endif
#endif
typedef struct {
kiss_fft_scalar r;
kiss_fft_scalar i;
}kiss_fft_cpx;
typedef struct kiss_fft_state* kiss_fft_cfg;
/*
* kiss_fft_alloc
*
* Initialize a FFT (or IFFT) algorithm's cfg/state buffer.
*
* typical usage: kiss_fft_cfg mycfg=kiss_fft_alloc(1024,0,NULL,NULL);
*
* The return value from fft_alloc is a cfg buffer used internally
* by the fft routine or NULL.
*
* If lenmem is NULL, then kiss_fft_alloc will allocate a cfg buffer using malloc.
* The returned value should be free()d when done to avoid memory leaks.
*
* The state can be placed in a user supplied buffer 'mem':
* If lenmem is not NULL and mem is not NULL and *lenmem is large enough,
* then the function places the cfg in mem and the size used in *lenmem
* and returns mem.
*
* If lenmem is not NULL and ( mem is NULL or *lenmem is not large enough),
* then the function returns NULL and places the minimum cfg
* buffer size in *lenmem.
* */
kiss_fft_cfg kiss_fft_alloc(int nfft,int inverse_fft,void * mem,size_t * lenmem);
/*
* kiss_fft(cfg,in_out_buf)
*
* Perform an FFT on a complex input buffer.
* for a forward FFT,
* fin should be f[0] , f[1] , ... ,f[nfft-1]
* fout will be F[0] , F[1] , ... ,F[nfft-1]
* Note that each element is complex and can be accessed like
f[k].r and f[k].i
* */
void kiss_fft(kiss_fft_cfg cfg,const kiss_fft_cpx *fin,kiss_fft_cpx *fout);
/*
A more generic version of the above function. It reads its input from every Nth sample.
* */
void kiss_fft_stride(kiss_fft_cfg cfg,const kiss_fft_cpx *fin,kiss_fft_cpx *fout,int fin_stride);
/* If kiss_fft_alloc allocated a buffer, it is one contiguous
buffer and can be simply free()d when no longer needed*/
#define kiss_fft_free free
/*
Cleans up some memory that gets managed internally. Not necessary to call, but it might clean up
your compiler output to call this before you exit.
*/
void kiss_fft_cleanup(void);
/*
* Returns the smallest integer k, such that k>=n and k has only "fast" factors (2,3,5)
*/
int kiss_fft_next_fast_size(int n);
/* for real ffts, we need an even size */
#define kiss_fftr_next_fast_size_real(n) \
(kiss_fft_next_fast_size( ((n)+1)>>1)<<1)
#ifdef __cplusplus
}
#endif
#endif

View File

@ -1,11 +0,0 @@
Copyright (c) 2003-2010 Mark Borgerding
All rights reserved.
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
* Neither the author nor the names of any contributors may be used to endorse or promote products derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

File diff suppressed because it is too large Load Diff

View File

@ -1,162 +0,0 @@
#ifndef WAVELET2D_H
#define WAVELET2D_H
#include <vector>
#include <complex>
using namespace std;
// the dll exports
#if defined WAVE_EXPORT
#define EXPORT __declspec(dllexport)
#else
#define EXPORT __declspec(dllimport)
#endif
// 1D Functions
EXPORT void* dwt1(string, vector<double> &, vector<double> &, vector<double> &);
EXPORT void* dyadic_zpad_1d(vector<double> &);
EXPORT double convol(vector<double> &, vector<double> &, vector<double> &);
EXPORT int filtcoef(string , vector<double> &, vector<double> &, vector<double> &,
vector<double> &);
EXPORT void downsamp(vector<double> &, int , vector<double> &);
EXPORT void upsamp(vector<double> &, int, vector<double> &);
EXPORT void circshift(vector<double> &, int );
EXPORT int sign(int);
EXPORT void* idwt1(string wname, vector<double> &, vector<double> &, vector<double> &);
EXPORT int vecsum(vector<double> &, vector<double> &, vector<double> &);
// 1D Symmetric Extension DWT Functions
EXPORT void* dwt_sym(vector<double> &, int ,string , vector<double> &,vector<double> &,
vector<int> &);
EXPORT void* dwt1_sym(string , vector<double> &, vector<double> &, vector<double> &);
EXPORT void* idwt_sym(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
EXPORT void* symm_ext(vector<double> &, int );
EXPORT void* idwt1_sym(string, vector<double> &, vector<double> &, vector<double> &); // Not Tested
// 1D Stationary Wavelet Transform
EXPORT void* swt(vector<double> &, int , string , vector<double> &, int &) ;
EXPORT void* iswt(vector<double> &,int , string, vector<double> &);
EXPORT void* per_ext(vector<double> &, int );
// 2D Functions
EXPORT void* branch_lp_dn(string , vector<double> &, vector<double> &);
EXPORT void* branch_hp_dn(string , vector<double> &, vector<double> &);
EXPORT void* branch_lp_hp_up(string ,vector<double> &, vector<double> &, vector<double> &);
//EXPORT void* dwt_2d(vector<vector<double> > &, int , string , vector<vector<double> > &
// , vector<double> &) ;
//EXPORT void* idwt_2d(vector<vector<double> > &,vector<double> &, string ,vector<vector<double> > &);
EXPORT void* dyadic_zpad_2d(vector<vector<double> > &,vector<vector<double> > &);
EXPORT void* dwt_output_dim(vector<vector<double> >&, int &, int & );
EXPORT void* zero_remove(vector<vector<double> > &,vector<vector<double> > &) ;
EXPORT void* getcoeff2d(vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &,vector<vector<double> > &,vector<double> &, int &);
EXPORT void* idwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* dwt2(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* downsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
EXPORT void* upsamp2(vector<vector<double> > &,vector<vector<double> > &, int, int);
// 2D DWT (Symmetric Extension) Functions
EXPORT void* dwt_2d_sym(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
EXPORT void* dwt2_sym(string ,vector<vector<double> > &, vector<vector<double> > &,
vector<vector<double> > &, vector<vector<double> > &, vector<vector<double> > &);
EXPORT void* idwt_2d_sym(vector<double> &,vector<double> &, string ,vector<vector<double> > &,
vector<int> &);
EXPORT void* circshift2d(vector<vector<double> > &, int , int );
EXPORT void symm_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
EXPORT void* dispDWT(vector<double> &,vector<vector<double> > &, vector<int> &, vector<int> &, int ) ;
EXPORT void* dwt_output_dim_sym(vector<int> &,vector<int> &, int );
//2D Stationary Wavelet Transform
EXPORT void* swt_2d(vector<vector<double> > &,int , string , vector<double> &);
EXPORT void* per_ext2d(vector<vector<double> > &,vector<vector<double> > &, int );
// FFT functions
EXPORT double convfft(vector<double> &, vector<double> &, vector<double> &);
EXPORT double convfftm(vector<double> &, vector<double> &, vector<double> &);
EXPORT void* fft(vector<complex<double> > &,int ,unsigned int);
EXPORT void* bitreverse(vector<complex<double> > &);
EXPORT void* freq(vector<double> &, vector<double> &);
//New
EXPORT void* dwt1_sym_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD);//FFTW3 for 2D
EXPORT void* idwt1_sym_m(string wname, vector<double> &X, vector<double> &app, vector<double> &detail);
EXPORT void* dwt(vector<double> &sig, int J, string nm, vector<double> &dwt_output
, vector<double> &flag, vector<int> &length );
EXPORT void* idwt(vector<double> &,vector<double> &, string,vector<double> &, vector<int> &);
EXPORT void* dwt_2d(vector<vector<double> > &, int , string , vector<double> &, vector<double> & ,
vector<int> &);
EXPORT void* dwt1_m(string wname, vector<double> &signal, vector<double> &cA, vector<double> &cD) ;
EXPORT void* idwt_2d(vector<double> &dwtop,vector<double> &flag, string nm,
vector<vector<double> > &idwt_output, vector<int> &length);
EXPORT void* idwt1_m(string wname, vector<double> &X, vector<double> &cA, vector<double> &cD);
EXPORT void* dwt_output_dim2(vector<int> &length, vector<int> &length2, int J);
#endif/* WAVELET2D_H */