-
Notifications
You must be signed in to change notification settings - Fork 112
/
Copy path04-image-spectrogram
executable file
·98 lines (74 loc) · 2.47 KB
/
04-image-spectrogram
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
#!/usr/bin/env python
"""
How to run:
mpirun -np <NUM> ./image-spectrogram <IMAGES.h5>
This example computes the 2D-FFT of every image inside <IMAGES.h5>,
Summs the absolute value of their spectrogram and finally displays
the result in log-scale.
"""
from __future__ import division
import sys
import tables
import pylab
import numpy as np
from numpy.fft import fft2, fftshift
from mpi4py import MPI
from parutils import pprint
#=============================================================================
# Main
comm = MPI.COMM_WORLD
in_fname = sys.argv[-1]
try:
h5in = tables.openFile(in_fname, 'r')
except:
pprint("Error: Could not open file %s" % in_fname)
exit(1)
images = h5in.root.images
image_count, height, width = images.shape
image_count = min(image_count, 800)
pprint("============================================================================")
pprint(" Running %d parallel MPI processes" % comm.size)
pprint(" Reading images from '%s'" % in_fname)
pprint(" Processing %d images of size %d x %d" % (image_count, width, height))
# Distribute workload so that each MPI process analyzes image number i, where
# i % comm.size == comm.rank.
#
# For example if comm.size == 4:
# rank 0: 0, 4, 8, ...
# rank 1: 1, 5, 9, ...
# rank 2: 2, 6, 10, ...
# rank 3: 3, 7, 11, ...
comm.Barrier() ### Start stopwatch ###
t_start = MPI.Wtime()
my_spec = np.zeros( (height, width) )
for i in range(comm.rank, image_count, comm.size):
img = images[i] # Load image from HDF file
img_ = fft2(img) # 2D FFT
my_spec += np.abs(img_) # Sum absolute value into partial spectrogram
my_spec /= image_count
# Now reduce the partial spectrograms into *spec* by summing
# them all together. The result is only avalable at rank 0.
# If you want the result to be availabe on all processes, use
# Allreduce(...)
spec = np.zeros_like(my_spec)
comm.Reduce(
[my_spec, MPI.DOUBLE],
[spec, MPI.DOUBLE],
op=MPI.SUM,
root=0
)
comm.Barrier()
t_diff = MPI.Wtime()-t_start ### Stop stopwatch ###
h5in.close()
pprint(
" Analyzed %d images in %5.2f seconds: %4.2f images per second" %
(image_count, t_diff, image_count/t_diff)
)
pprint("============================================================================")
# Now rank 0 outputs the resulting spectrogram.
# Either onto the screen or into a image file.
if comm.rank == 0:
spec = fftshift(spec)
pylab.imshow(np.log(spec))
pylab.show()
comm.Barrier()