Illustrate the scale property of the Discrete Fourier Transform.
The scale property of the Discrete Fourier Transform (DFT) is not the same as in the continuous Fourier Transform. In the discrete case the property is the following. If the image is enlarged in such a way that the new pixels have value zero, then its DFT is filled with a replication of the original DFT. In this demonstration, a small original image is expanded and its DFT is compared to the replicated DFT of the original image. The results should be the same.
In [1]:
%matplotlib inline
import numpy as np
import matplotlib.pyplot as plt
import matplotlib.image as mpimg
import sys,os
ia898path = os.path.abspath('../../')
if ia898path not in sys.path:
sys.path.append(ia898path)
import ia898.src as ia
In [2]:
f = mpimg.imread('../data/cameraman.tif')
froi = f[19:19+64,99:99+64] # ROI selection
plt.imshow(f,cmap='gray');
In [3]:
plt.imshow(froi,cmap='gray')
plt.colorbar();
In [15]:
nb = ia.nbshow(2)
nb.nbshow(f,'original',)
nb.nbshow(froi,'pequena')
nb.nbshow()
In [16]:
fd = froi.astype(float)
F = np.fft.fft2(fd) # F is the DFT of f
#F = ia.dft(fd)
ia.adshow(froi)
ia.adshow(ia.dftview(F))
In [23]:
H,W = froi.shape
fx4 = np.zeros((4*H,4*W),'uint8') # size is 4 times larger
fx4[::4,::4] = froi # filling the expanded image
ia.adshow(froi)
ia.adshow(fx4)
print(fx4.mean(),froi.mean())
In [25]:
fdx4 = fx4.astype(float)
Fx4 = np.fft.fft2(fdx4) # Fx4 is the DFT of fx4 (expanded f)
ia.adshow(ia.dftview(F))
ia.adshow(ia.dftview(Fx4))
In [26]:
aux = np.concatenate((F,F,F,F))
FFx4 = np.concatenate((aux,aux,aux,aux), 1) # replicate the DFT of f
ia.adshow(ia.dftview(FFx4))
diff = abs(FFx4 - Fx4).sum() # compare the replicated DFT with DFT of expanded f
print(diff) # print the error signal power
In [27]:
ffdx4 = np.fft.ifft2(FFx4)
fimag = ffdx4.imag
print(fimag.sum())
ffdx4 = np.floor(0.5 + ffdx4.real) # round
ia.adshow(ia.normalize(ffdx4.astype('int32')))
error = abs(fdx4 - ffdx4).sum()
print(error)
In [ ]:
In [ ]: