Skip to content

Commit b29f021

Browse files
authored
Merge pull request #14 from joeljonsson/develop
update master
2 parents 927317b + 07dcfc5 commit b29f021

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

51 files changed

+2508
-3871
lines changed

.gitmodules

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
[submodule "LibAPR"]
22
path = LibAPR
33
url = https://github.com/AdaptiveParticles/LibAPR.git
4-
branch = develop
4+
branch = develop_joel
55
[submodule "pybind11"]
66
path = pybind11
77
url = https://github.com/pybind/pybind11.git
8+
branch = master

CMakeLists.txt

Lines changed: 21 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ set(CMAKE_CXX_STANDARD 14)
66

77
# APR build options:
88
option(PYAPR_USE_OPENMP "Use OpenMP for PyAPR functionality" ON)
9+
option(PYAPR_USE_CUDA "Use CUDA for PyAPR functionality" OFF)
910

1011
##------------- Required libraries -------------##
1112
find_package(HDF5 REQUIRED)
@@ -23,16 +24,16 @@ set(APR_TESTS OFF CACHE BOOL "" FORCE)
2324
set(APR_BUILD_STATIC_LIB ON CACHE BOOL "" FORCE)
2425
set(APR_BUILD_SHARED_LIB OFF CACHE BOOL "" FORCE)
2526
set(APR_BUILD_EXAMPLES OFF CACHE BOOL "" FORCE)
26-
set(APR_USE_CUDA OFF CACHE BOOL "" FORCE)
2727
set(APR_BUILD_PYTHON_WRAPPERS OFF CACHE BOOL "" FORCE)
2828
set(APR_USE_LIBTIFF ON CACHE BOOL "" FORCE)
29-
set(APR_USE_OPENMP ON CACHE BOOL "" FORCE)
29+
set(APR_USE_OPENMP ${PYAPR_USE_OPENMP} CACHE BOOL "" FORCE)
30+
set(APR_USE_CUDA ${PYAPR_USE_CUDA} CACHE BOOL "" FORCE)
3031

3132
include_directories(${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_BINARY_DIR}/LibAPR ${HDF5_INCLUDE_DIRS} ${ZLIB_INCLUDE_DIRS} ${TIFF_INCLUDE_DIR})
3233

3334
add_subdirectory("LibAPR")
3435
include_directories(LibAPR/src)
35-
36+
include_directories("LibAPR/external/glm")
3637

3738
###############################################################################
3839
# Handle OpenMP
@@ -41,11 +42,26 @@ find_package(OpenMP)
4142
if(NOT OPENMP_FOUND OR NOT PYAPR_USE_OPENMP)
4243
message(WARNING "OpenMP support not found or disabled with current compiler. While PyAPR can compile like this, performance might not be optimal. Please see README.md for instructions.")
4344
else()
44-
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DPYAPR_HAVE_OPENMP ${OpenMP_C_FLAGS}")
45-
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DPYAPR_HAVE_OPENMP ${OpenMP_CXX_FLAGS}")
45+
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DPYAPR_HAVE_OPENMP -DHAVE_OPENMP ${OpenMP_C_FLAGS}")
46+
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DPYAPR_HAVE_OPENMP -DHAVE_OPENMP ${OpenMP_CXX_FLAGS}")
4647
endif()
4748

4849

50+
###############################################################################
51+
# Handle CUDA
52+
###############################################################################
53+
if(PYAPR_USE_CUDA)
54+
message(STATUS "APR: Building CUDA for PYAPR")
55+
set(CMAKE_CUDA_STANDARD 14)
56+
set(CMAKE_CUDA_RUNTIME_LIBRARY "Static")
57+
set(CMAKE_CUDA_FLAGS "${CMAKE_CUDA_FLAGS} --default-stream per-thread -lineinfo -Xptxas -O3,-v --use_fast_math -DPYAPR_USE_CUDA -DAPR_USE_CUDA")
58+
59+
enable_language(CUDA)
60+
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DPYAPR_USE_CUDA -DAPR_USE_CUDA")
61+
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DPYAPR_USE_CUDA -DAPR_USE_CUDA")
62+
include_directories(${CMAKE_CUDA_TOOLKIT_INCLUDE_DIRECTORIES})
63+
64+
endif()
4965

5066
###############################################################################
5167
# Configure compiler options

LibAPR

Submodule LibAPR updated 176 files

demo/apr_io_demo.py

Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
import pyapr
2+
import numpy as np
3+
from skimage import io as skio
4+
5+
6+
def main():
7+
8+
# Read in an image
9+
io_int = pyapr.filegui.InteractiveIO()
10+
fpath = io_int.get_tiff_file_name()
11+
img = skio.imread(fpath).astype(np.uint16)
12+
13+
# Initialize objects
14+
apr = pyapr.APR()
15+
parts = pyapr.ShortParticles()
16+
par = pyapr.APRParameters()
17+
converter = pyapr.converter.ShortConverter()
18+
19+
# Set some parameters
20+
par.auto_parameters = False
21+
par.rel_error = 0.1
22+
par.Ip_th = 10
23+
par.grad_th = 50
24+
par.gradient_smoothing = 2
25+
par.sigma_th = 100
26+
par.sigma_th_max = 50
27+
converter.set_parameters(par)
28+
converter.set_verbose(False)
29+
30+
# Compute APR and sample particle values
31+
converter.get_apr(apr, img)
32+
33+
# Compute and display the computational ratio
34+
numParts = apr.total_number_particles()
35+
numPix = img.size
36+
CR = numPix / numParts
37+
38+
print('input image size: {} pixels, APR size: {} particles --> Computational Ratio: {}'.format(numPix, numParts, CR))
39+
40+
# Sample particle intensities
41+
parts.sample_image(apr, img)
42+
43+
# Save the APR to file
44+
fpath_apr = io_int.save_apr_file_name()
45+
46+
# Initialize APRFile for I/O
47+
aprfile = pyapr.io.APRFile()
48+
aprfile.set_read_write_tree(True)
49+
50+
# Write APR and particles to file
51+
aprfile.open(fpath_apr, 'WRITE')
52+
aprfile.write_apr(apr)
53+
aprfile.write_particles('particles', parts)
54+
aprfile.close()
55+
56+
# Read the newly written file
57+
58+
# Initialize objects for reading in data
59+
apr2 = pyapr.APR()
60+
parts2 = pyapr.ShortParticles()
61+
62+
# Read from APR file
63+
aprfile.open(fpath_apr, 'READ')
64+
aprfile.read_apr(apr2)
65+
aprfile.read_particles(apr2, 'particles', parts2)
66+
aprfile.close()
67+
68+
# Reconstruct pixel image
69+
tmp = pyapr.numerics.reconstruction.recon_pc(apr, parts)
70+
recon = np.array(tmp, copy=False)
71+
72+
73+
if __name__ == '__main__':
74+
main()

demo/apr_iteration_demo.py

Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
import pyapr
2+
import numpy as np
3+
from time import time
4+
5+
6+
def main():
7+
8+
io_int = pyapr.filegui.InteractiveIO()
9+
fpath_apr = io_int.get_apr_file_name() # get APR file path from gui
10+
11+
aprfile = pyapr.io.APRFile()
12+
aprfile.set_read_write_tree(True)
13+
14+
# Initialize APR and particle objects
15+
parts = pyapr.ShortParticles()
16+
apr = pyapr.APR()
17+
18+
# Read from APR file
19+
aprfile.open(fpath_apr, 'READ')
20+
aprfile.read_apr(apr)
21+
aprfile.read_particles(apr, 'particles', parts)
22+
aprfile.close()
23+
24+
start = time()
25+
26+
org_dims = apr.org_dims() # (Ny, Nx, Nz)
27+
py_recon = np.empty((org_dims[2], org_dims[1], org_dims[0]), dtype=np.uint16)
28+
max_level = apr.level_max()
29+
30+
apr_it = apr.iterator()
31+
32+
# loop over levels up to level_max-1
33+
for level in range(apr_it.level_min(), apr_it.level_max()):
34+
35+
step_size = 2 ** (max_level - level)
36+
37+
for z in range(apr_it.z_num(level)):
38+
for x in range(apr_it.x_num(level)):
39+
for idx in range(apr_it.begin(level, z, x), apr_it.end()):
40+
y = apr_it.y(idx) # this is slow
41+
42+
y_start = y * step_size
43+
x_start = x * step_size
44+
z_start = z * step_size
45+
46+
y_end = min(y_start+step_size, py_recon.shape[2])
47+
x_end = min(x_start+step_size, py_recon.shape[1])
48+
z_end = min(z_start+step_size, py_recon.shape[0])
49+
50+
py_recon[z_start:z_end, x_start:x_end, y_start:y_end] = parts[idx]
51+
52+
# particles at the maximum level coincide with pixels
53+
level = max_level
54+
for z in range(apr_it.z_num(level)):
55+
for x in range(apr_it.x_num(level)):
56+
for idx in range(apr_it.begin(level, z, x), apr_it.end()):
57+
py_recon[z, x, apr_it.y(idx)] = parts[idx]
58+
59+
py_time = time()-start
60+
print('python reconstruction took {} seconds'.format(py_time))
61+
62+
start = time()
63+
tmp = pyapr.numerics.reconstruction.recon_pc(apr, parts)
64+
cpp_recon = np.array(tmp, copy=False)
65+
cpp_time = time()-start
66+
print('c++ reconstruction took {} seconds'.format(cpp_time))
67+
print('c++ was {} times faster'.format(py_time / cpp_time))
68+
69+
zm = min(org_dims[2], 128)
70+
xm = min(org_dims[1], 128)
71+
ym = min(org_dims[0], 128)
72+
73+
success = np.allclose(py_recon[:zm, :xm, :ym], cpp_recon[:zm, :xm, :ym])
74+
if not success:
75+
print('Python and C++ reconstructions give different results...')
76+
77+
78+
if __name__ == '__main__':
79+
main()

demo/basic.py

Lines changed: 0 additions & 62 deletions
This file was deleted.

demo/compress_particles_demo.py

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
import pyapr
2+
3+
4+
def main():
5+
6+
io_int = pyapr.filegui.InteractiveIO()
7+
fpath_apr = io_int.get_apr_file_name() # get APR file path from gui
8+
9+
# Initialize objects
10+
apr = pyapr.APR()
11+
parts = pyapr.ShortParticles()
12+
13+
# Initialize APRFile for I/O
14+
aprfile = pyapr.io.APRFile()
15+
aprfile.set_read_write_tree(True)
16+
17+
# Read APR and particles from file
18+
aprfile.open(fpath_apr, 'READ')
19+
aprfile.read_apr(apr)
20+
aprfile.read_particles(apr, 'particles', parts)
21+
22+
original_file_size = aprfile.current_file_size_MB()
23+
aprfile.close()
24+
25+
# Interactive WNL compression
26+
pyapr.viewer.interactive_compression(apr, parts)
27+
28+
# Write compressed APR to file
29+
fpath_apr_save = io_int.save_apr_file_name() # get file path from gui
30+
31+
aprfile.open(fpath_apr_save, 'WRITE')
32+
aprfile.write_apr(apr) # need to write the unchanged apr structure
33+
aprfile.write_particles('particles', parts)
34+
35+
compressed_file_size = aprfile.current_file_size_MB()
36+
aprfile.close()
37+
38+
# Uncompressed pixel image size in MB
39+
original_image_size = 2e-6 * apr.x_num(apr.level_max()) * apr.y_num(apr.level_max()) * apr.z_num(apr.level_max())
40+
41+
print("Original File Size: {:7.2f} MB".format(original_file_size))
42+
print("Lossy Compressed File Size: {:7.2f} MB".format(compressed_file_size))
43+
44+
# compare uncompressed pixel image size to compressed APR file sizes
45+
print("Original Memory Compression Ratio: {:7.2f} ".format(original_image_size/original_file_size))
46+
print("Lossy Memory Compression Ratio: {:7.2f} ".format(original_image_size/compressed_file_size))
47+
48+
49+
if __name__ == '__main__':
50+
main()

0 commit comments

Comments
 (0)