biomedisa 24.8.6__tar.gz → 24.8.8__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {biomedisa-24.8.6 → biomedisa-24.8.8}/PKG-INFO +10 -8
- {biomedisa-24.8.6 → biomedisa-24.8.8}/README.md +7 -5
- {biomedisa-24.8.6 → biomedisa-24.8.8}/pyproject.toml +2 -2
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/deeplearning.py +17 -6
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/keras_helper.py +242 -165
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa.egg-info/PKG-INFO +10 -8
- {biomedisa-24.8.6 → biomedisa-24.8.8}/LICENSE +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/setup.cfg +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/__init__.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/__main__.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/DataGenerator.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/DataGeneratorCrop.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/PredictDataGenerator.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/PredictDataGeneratorCrop.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/__init__.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/active_contour.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/amira_to_np/__init__.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/amira_to_np/amira_data_stream.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/amira_to_np/amira_grammar.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/amira_to_np/amira_header.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/amira_to_np/amira_helper.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/assd.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/biomedisa_helper.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/create_slices.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/crop_helper.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/curvop_numba.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/django_env.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/nc_reader.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/pid.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/process_image.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/pycuda_test.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/__init__.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/gpu_kernels.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/pycuda_large.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/pycuda_large_allx.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/pycuda_small.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/pycuda_small_allx.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/pyopencl_large.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/pyopencl_small.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/rw_large.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/rw_small.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/remove_outlier.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/split_volume.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/interpolation.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/mesh.py +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa.egg-info/SOURCES.txt +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa.egg-info/dependency_links.txt +0 -0
- {biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa.egg-info/top_level.txt +0 -0
@@ -1,6 +1,6 @@
|
|
1
|
-
Metadata-Version: 2.
|
1
|
+
Metadata-Version: 2.2
|
2
2
|
Name: biomedisa
|
3
|
-
Version: 24.8.
|
3
|
+
Version: 24.8.8
|
4
4
|
Summary: Segmentation of 3D volumetric image data
|
5
5
|
Author: Philipp Lösel
|
6
6
|
Author-email: philipp.loesel@anu.edu.au
|
@@ -10,7 +10,7 @@ Project-URL: GitHub, https://github.com/biomedisa/biomedisa
|
|
10
10
|
Classifier: Programming Language :: Python :: 3
|
11
11
|
Classifier: License :: OSI Approved :: European Union Public Licence 1.2 (EUPL 1.2)
|
12
12
|
Classifier: Operating System :: OS Independent
|
13
|
-
Requires-Python: >=3.
|
13
|
+
Requires-Python: >=3.10
|
14
14
|
Description-Content-Type: text/markdown
|
15
15
|
License-File: LICENSE
|
16
16
|
|
@@ -19,6 +19,7 @@ License-File: LICENSE
|
|
19
19
|
- [Overview](#overview)
|
20
20
|
- [Hardware Requirements](#hardware-requirements)
|
21
21
|
- [Installation (command-line based)](#installation-command-line-based)
|
22
|
+
- [Installation (3D Slicer extension)](#installation-3d-slicer-extension)
|
22
23
|
- [Installation (browser based)](#installation-browser-based)
|
23
24
|
- [Download Data](#download-data)
|
24
25
|
- [Revisions](#revisions)
|
@@ -33,14 +34,15 @@ License-File: LICENSE
|
|
33
34
|
- [License](#license)
|
34
35
|
|
35
36
|
## Overview
|
36
|
-
Biomedisa (https://biomedisa.info) is a free and easy-to-use open-source application for segmenting large 3D volumetric images such as CT and MRI scans, developed at [The Australian National University CTLab](https://ctlab.anu.edu.au/). Biomedisa's smart interpolation of sparsely pre-segmented slices enables accurate semi-automated segmentation by considering the complete underlying image data. Additionally, Biomedisa enables deep learning for fully automated segmentation across similar samples and structures. It is compatible with segmentation tools like Amira/Avizo, ImageJ/Fiji and 3D Slicer. If you are using Biomedisa or the data for your research please cite: Lösel, P.D. et al. [Introducing Biomedisa as an open-source online platform for biomedical image segmentation.](https://www.nature.com/articles/s41467-020-19303-w) *Nat. Commun.* **11**, 5577 (2020).
|
37
|
+
Biomedisa (https://biomedisa.info) is a free and easy-to-use open-source application for segmenting large 3D volumetric images such as CT and MRI scans, developed at [The Australian National University CTLab](https://ctlab.anu.edu.au/). Biomedisa's smart interpolation of sparsely pre-segmented slices enables accurate semi-automated segmentation by considering the complete underlying image data. Additionally, Biomedisa enables deep learning for fully automated segmentation across similar samples and structures. It is compatible with segmentation tools like Amira/Avizo, ImageJ/Fiji, and 3D Slicer. If you are using Biomedisa or the data for your research please cite: Lösel, P.D. et al. [Introducing Biomedisa as an open-source online platform for biomedical image segmentation.](https://www.nature.com/articles/s41467-020-19303-w) *Nat. Commun.* **11**, 5577 (2020).
|
37
38
|
|
38
39
|
## Hardware Requirements
|
39
|
-
+ One or more NVIDIA GPUs
|
40
|
+
+ One or more NVIDIA GPUs.
|
40
41
|
|
41
42
|
## Installation (command-line based)
|
42
|
-
+ [Ubuntu 22
|
43
|
-
+ [Ubuntu 22
|
43
|
+
+ [Ubuntu 22/24 + Smart Interpolation](https://github.com/biomedisa/biomedisa/blob/master/README/ubuntu_interpolation_cli.md)
|
44
|
+
+ [Ubuntu 22/24 + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/ubuntu_deeplearning_cli.md)
|
45
|
+
+ [Ubuntu 22/24 + Smart Interpolation + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/ubuntu_cli.md)
|
44
46
|
+ [Windows 10/11 + Smart Interpolation + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/windows10_cuda_gpu_cli.md)
|
45
47
|
+ [Windows (WSL) + Smart Interpolation + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/windows_wsl.md)
|
46
48
|
|
@@ -165,7 +167,7 @@ save_data('final.Head5.am', results['regular'], results['header'])
|
|
165
167
|
|
166
168
|
#### Command-line based (prediction)
|
167
169
|
```
|
168
|
-
python -m biomedisa.deeplearning C:\Users\%USERNAME%\Downloads\testing_axial_crop_pat13.nii.gz C:\Users\%USERNAME%\Downloads\heart.h5
|
170
|
+
python -m biomedisa.deeplearning C:\Users\%USERNAME%\Downloads\testing_axial_crop_pat13.nii.gz C:\Users\%USERNAME%\Downloads\heart.h5
|
169
171
|
```
|
170
172
|
|
171
173
|
## Mesh Generator
|
@@ -3,6 +3,7 @@
|
|
3
3
|
- [Overview](#overview)
|
4
4
|
- [Hardware Requirements](#hardware-requirements)
|
5
5
|
- [Installation (command-line based)](#installation-command-line-based)
|
6
|
+
- [Installation (3D Slicer extension)](#installation-3d-slicer-extension)
|
6
7
|
- [Installation (browser based)](#installation-browser-based)
|
7
8
|
- [Download Data](#download-data)
|
8
9
|
- [Revisions](#revisions)
|
@@ -17,14 +18,15 @@
|
|
17
18
|
- [License](#license)
|
18
19
|
|
19
20
|
## Overview
|
20
|
-
Biomedisa (https://biomedisa.info) is a free and easy-to-use open-source application for segmenting large 3D volumetric images such as CT and MRI scans, developed at [The Australian National University CTLab](https://ctlab.anu.edu.au/). Biomedisa's smart interpolation of sparsely pre-segmented slices enables accurate semi-automated segmentation by considering the complete underlying image data. Additionally, Biomedisa enables deep learning for fully automated segmentation across similar samples and structures. It is compatible with segmentation tools like Amira/Avizo, ImageJ/Fiji and 3D Slicer. If you are using Biomedisa or the data for your research please cite: Lösel, P.D. et al. [Introducing Biomedisa as an open-source online platform for biomedical image segmentation.](https://www.nature.com/articles/s41467-020-19303-w) *Nat. Commun.* **11**, 5577 (2020).
|
21
|
+
Biomedisa (https://biomedisa.info) is a free and easy-to-use open-source application for segmenting large 3D volumetric images such as CT and MRI scans, developed at [The Australian National University CTLab](https://ctlab.anu.edu.au/). Biomedisa's smart interpolation of sparsely pre-segmented slices enables accurate semi-automated segmentation by considering the complete underlying image data. Additionally, Biomedisa enables deep learning for fully automated segmentation across similar samples and structures. It is compatible with segmentation tools like Amira/Avizo, ImageJ/Fiji, and 3D Slicer. If you are using Biomedisa or the data for your research please cite: Lösel, P.D. et al. [Introducing Biomedisa as an open-source online platform for biomedical image segmentation.](https://www.nature.com/articles/s41467-020-19303-w) *Nat. Commun.* **11**, 5577 (2020).
|
21
22
|
|
22
23
|
## Hardware Requirements
|
23
|
-
+ One or more NVIDIA GPUs
|
24
|
+
+ One or more NVIDIA GPUs.
|
24
25
|
|
25
26
|
## Installation (command-line based)
|
26
|
-
+ [Ubuntu 22
|
27
|
-
+ [Ubuntu 22
|
27
|
+
+ [Ubuntu 22/24 + Smart Interpolation](https://github.com/biomedisa/biomedisa/blob/master/README/ubuntu_interpolation_cli.md)
|
28
|
+
+ [Ubuntu 22/24 + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/ubuntu_deeplearning_cli.md)
|
29
|
+
+ [Ubuntu 22/24 + Smart Interpolation + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/ubuntu_cli.md)
|
28
30
|
+ [Windows 10/11 + Smart Interpolation + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/windows10_cuda_gpu_cli.md)
|
29
31
|
+ [Windows (WSL) + Smart Interpolation + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/windows_wsl.md)
|
30
32
|
|
@@ -149,7 +151,7 @@ save_data('final.Head5.am', results['regular'], results['header'])
|
|
149
151
|
|
150
152
|
#### Command-line based (prediction)
|
151
153
|
```
|
152
|
-
python -m biomedisa.deeplearning C:\Users\%USERNAME%\Downloads\testing_axial_crop_pat13.nii.gz C:\Users\%USERNAME%\Downloads\heart.h5
|
154
|
+
python -m biomedisa.deeplearning C:\Users\%USERNAME%\Downloads\testing_axial_crop_pat13.nii.gz C:\Users\%USERNAME%\Downloads\heart.h5
|
153
155
|
```
|
154
156
|
|
155
157
|
## Mesh Generator
|
@@ -4,13 +4,13 @@ build-backend = "setuptools.build_meta"
|
|
4
4
|
|
5
5
|
[project]
|
6
6
|
name = "biomedisa"
|
7
|
-
version = "24.8.
|
7
|
+
version = "24.8.8"
|
8
8
|
authors = [
|
9
9
|
{ name="Philipp Lösel"}, {email="philipp.loesel@anu.edu.au" },
|
10
10
|
]
|
11
11
|
description = "Segmentation of 3D volumetric image data"
|
12
12
|
readme = "README.md"
|
13
|
-
requires-python = ">=3.
|
13
|
+
requires-python = ">=3.10"
|
14
14
|
classifiers = [
|
15
15
|
"Programming Language :: Python :: 3",
|
16
16
|
"License :: OSI Approved :: European Union Public Licence 1.2 (EUPL 1.2)",
|
@@ -71,7 +71,7 @@ def deep_learning(img_data, label_data=None, val_img_data=None, val_label_data=N
|
|
71
71
|
learning_rate=0.01, stride_size=32, validation_stride_size=32, validation_freq=1,
|
72
72
|
batch_size=None, x_scale=256, y_scale=256, z_scale=256, scaling=True, early_stopping=0,
|
73
73
|
pretrained_model=None, fine_tune=False, workers=1, cropping_epochs=50,
|
74
|
-
x_range=None, y_range=None, z_range=None, header=None, extension=
|
74
|
+
x_range=None, y_range=None, z_range=None, header=None, extension=None,
|
75
75
|
img_header=None, img_extension='.tif', average_dice=False, django_env=False,
|
76
76
|
path=None, success=True, return_probs=False, patch_normalization=False,
|
77
77
|
z_patch=64, y_patch=64, x_patch=64, path_to_logfile=None, img_id=None, label_id=None,
|
@@ -228,9 +228,11 @@ def deep_learning(img_data, label_data=None, val_img_data=None, val_label_data=N
|
|
228
228
|
bm.scaling = bool(meta['scaling'][()])
|
229
229
|
|
230
230
|
# check if amira header is available in the network
|
231
|
-
if bm.header is None and meta.get('header') is not None:
|
231
|
+
if bm.extension is None and bm.header is None and meta.get('header') is not None:
|
232
232
|
bm.header = [np.array(meta.get('header'))]
|
233
233
|
bm.extension = '.am'
|
234
|
+
if bm.extension is None:
|
235
|
+
bm.extension = '.tif'
|
234
236
|
|
235
237
|
# crop data
|
236
238
|
crop_data = True if 'cropping_weights' in hf else False
|
@@ -301,6 +303,12 @@ def deep_learning(img_data, label_data=None, val_img_data=None, val_label_data=N
|
|
301
303
|
results, bm = predict_segmentation(bm, region_of_interest,
|
302
304
|
channels, normalization_parameters)
|
303
305
|
|
306
|
+
from mpi4py import MPI
|
307
|
+
comm = MPI.COMM_WORLD
|
308
|
+
rank = comm.Get_rank()
|
309
|
+
if rank>0:
|
310
|
+
return 0
|
311
|
+
|
304
312
|
# results
|
305
313
|
if cropped_volume is not None:
|
306
314
|
results['cropped_volume'] = cropped_volume
|
@@ -361,7 +369,7 @@ if __name__ == '__main__':
|
|
361
369
|
parser.add_argument('path_to_images', type=str, metavar='PATH_TO_IMAGES',
|
362
370
|
help='Location of image data (tarball, directory, or file)')
|
363
371
|
parser.add_argument('path', type=str, metavar='PATH',
|
364
|
-
help='Location of label data
|
372
|
+
help='Location of label data for training (tarball, directory, or file) or model for prediction (.h5)')
|
365
373
|
|
366
374
|
# optional arguments
|
367
375
|
g.add_argument('-p','--predict', action='store_true', default=False,
|
@@ -488,8 +496,10 @@ if __name__ == '__main__':
|
|
488
496
|
help='Location of mask')
|
489
497
|
parser.add_argument('-rf','--refinement', action='store_true', default=False,
|
490
498
|
help='Refine segmentation on full size data')
|
491
|
-
parser.add_argument('-ext','--extension', type=str, default=
|
492
|
-
help='Save data
|
499
|
+
parser.add_argument('-ext','--extension', type=str, default=None,
|
500
|
+
help='Save data in formats like NRRD or TIFF using --extension=".nrrd"')
|
501
|
+
parser.add_argument('-ptm','--path_to_model', type=str, metavar='PATH', default=None,
|
502
|
+
help='Specify the model location for training')
|
493
503
|
bm = parser.parse_args()
|
494
504
|
bm.success = True
|
495
505
|
|
@@ -505,7 +515,8 @@ if __name__ == '__main__':
|
|
505
515
|
bm.path_to_model = bm.path
|
506
516
|
if bm.train:
|
507
517
|
bm.path_to_labels = bm.path
|
508
|
-
bm.path_to_model
|
518
|
+
if bm.path_to_model is None:
|
519
|
+
bm.path_to_model = bm.path_to_images + '.h5'
|
509
520
|
|
510
521
|
# django environment
|
511
522
|
if bm.img_id is not None:
|
@@ -424,8 +424,6 @@ def load_training_data(bm, img_list, label_list, channels, img_in=None, label_in
|
|
424
424
|
|
425
425
|
# if header is not single data stream Amira Mesh falling back to Multi-TIFF
|
426
426
|
if extension != '.am':
|
427
|
-
if extension != '.tif':
|
428
|
-
print(f'Warning! Please use --header_file="path_to_training_label{extension}" for prediction to save your result as "{extension}"')
|
429
427
|
extension, header = '.tif', None
|
430
428
|
elif len(header) > 1:
|
431
429
|
print('Warning! Multiple data streams are not supported. Falling back to TIFF.')
|
@@ -798,6 +796,35 @@ class Metrics(Callback):
|
|
798
796
|
if self.early_stopping > 0 and max(self.history['val_dice']) not in self.history['val_dice'][-self.early_stopping:]:
|
799
797
|
self.model.stop_training = True
|
800
798
|
|
799
|
+
class HistoryCallback(Callback):
|
800
|
+
def __init__(self, bm):
|
801
|
+
self.path_to_model = bm.path_to_model
|
802
|
+
self.train_dice = bm.train_dice
|
803
|
+
self.val_img_data = bm.val_img_data
|
804
|
+
|
805
|
+
def on_train_begin(self, logs={}):
|
806
|
+
self.history = {}
|
807
|
+
self.history['loss'] = []
|
808
|
+
self.history['accuracy'] = []
|
809
|
+
if self.train_dice:
|
810
|
+
self.history['dice'] = []
|
811
|
+
if self.val_img_data is not None:
|
812
|
+
self.history['val_loss'] = []
|
813
|
+
self.history['val_accuracy'] = []
|
814
|
+
|
815
|
+
def on_epoch_end(self, epoch, logs={}):
|
816
|
+
# append history
|
817
|
+
self.history['loss'].append(logs['loss'])
|
818
|
+
self.history['accuracy'].append(logs['accuracy'])
|
819
|
+
if self.train_dice:
|
820
|
+
self.history['dice'].append(logs['dice'])
|
821
|
+
if self.val_img_data is not None:
|
822
|
+
self.history['val_loss'].append(logs['val_loss'])
|
823
|
+
self.history['val_accuracy'].append(logs['val_accuracy'])
|
824
|
+
|
825
|
+
# plot history in figure and save as numpy array
|
826
|
+
save_history(self.history, self.path_to_model)
|
827
|
+
|
801
828
|
def softmax(x):
|
802
829
|
# Avoiding numerical instability by subtracting the maximum value
|
803
830
|
exp_values = np.exp(x - np.max(x, axis=-1, keepdims=True))
|
@@ -1020,11 +1047,11 @@ def train_segmentation(bm):
|
|
1020
1047
|
monitor='val_accuracy',
|
1021
1048
|
mode='max',
|
1022
1049
|
save_best_only=True)
|
1023
|
-
callbacks = [model_checkpoint_callback, meta_data]
|
1050
|
+
callbacks = [model_checkpoint_callback, HistoryCallback(bm), meta_data]
|
1024
1051
|
if bm.early_stopping > 0:
|
1025
1052
|
callbacks.insert(0, EarlyStopping(monitor='val_accuracy', mode='max', patience=bm.early_stopping))
|
1026
1053
|
else:
|
1027
|
-
callbacks = [ModelCheckpoint(filepath=str(bm.path_to_model)), meta_data]
|
1054
|
+
callbacks = [ModelCheckpoint(filepath=str(bm.path_to_model)), HistoryCallback(bm), meta_data]
|
1028
1055
|
|
1029
1056
|
# monitor dice score on training data
|
1030
1057
|
if bm.train_dice:
|
@@ -1035,15 +1062,11 @@ def train_segmentation(bm):
|
|
1035
1062
|
callbacks.insert(-1, CustomCallback(bm.img_id, bm.epochs))
|
1036
1063
|
|
1037
1064
|
# train model
|
1038
|
-
|
1039
|
-
|
1040
|
-
|
1041
|
-
|
1042
|
-
|
1043
|
-
|
1044
|
-
# save monitoring figure on train end
|
1045
|
-
if bm.val_img_data is None or not bm.val_dice:
|
1046
|
-
save_history(history.history, bm.path_to_model)
|
1065
|
+
model.fit(training_generator,
|
1066
|
+
epochs=bm.epochs,
|
1067
|
+
validation_data=validation_generator,
|
1068
|
+
callbacks=callbacks,
|
1069
|
+
workers=bm.workers)
|
1047
1070
|
|
1048
1071
|
def load_prediction_data(bm, channels, normalize, normalization_parameters,
|
1049
1072
|
region_of_interest, img, img_header, load_blockwise=False, z=None):
|
@@ -1151,6 +1174,21 @@ def gradient(volData):
|
|
1151
1174
|
|
1152
1175
|
def predict_segmentation(bm, region_of_interest, channels, normalization_parameters):
|
1153
1176
|
|
1177
|
+
from mpi4py import MPI
|
1178
|
+
comm = MPI.COMM_WORLD
|
1179
|
+
rank = comm.Get_rank()
|
1180
|
+
ngpus = comm.Get_size()
|
1181
|
+
|
1182
|
+
# Set the visible GPU by ID
|
1183
|
+
gpus = tf.config.experimental.list_physical_devices('GPU')
|
1184
|
+
if gpus:
|
1185
|
+
try:
|
1186
|
+
# Restrict TensorFlow to only use the specified GPU
|
1187
|
+
tf.config.experimental.set_visible_devices(gpus[rank], 'GPU')
|
1188
|
+
tf.config.experimental.set_memory_growth(gpus[rank], True)
|
1189
|
+
except RuntimeError as e:
|
1190
|
+
print(e)
|
1191
|
+
|
1154
1192
|
# initialize results
|
1155
1193
|
results = {}
|
1156
1194
|
|
@@ -1177,6 +1215,7 @@ def predict_segmentation(bm, region_of_interest, channels, normalization_paramet
|
|
1177
1215
|
load_blockwise = False
|
1178
1216
|
if not bm.scaling and not bm.normalize and bm.path_to_image and not np.any(region_of_interest) and \
|
1179
1217
|
os.path.splitext(bm.path_to_image)[1] in ['.tif', '.tiff'] and not bm.acwe:
|
1218
|
+
# get image shape
|
1180
1219
|
tif = TiffFile(bm.path_to_image)
|
1181
1220
|
zsh = len(tif.pages)
|
1182
1221
|
ysh, xsh = tif.pages[0].shape
|
@@ -1292,17 +1331,23 @@ def predict_segmentation(bm, region_of_interest, channels, normalization_paramet
|
|
1292
1331
|
# stream data batchwise to GPU to reduce memory usage
|
1293
1332
|
X = np.empty((bm.batch_size, bm.z_patch, bm.y_patch, bm.x_patch, channels), dtype=np.float32)
|
1294
1333
|
|
1295
|
-
# allocate final array
|
1296
|
-
if bm.return_probs:
|
1334
|
+
# allocate final probabilities array
|
1335
|
+
if rank==0 and bm.return_probs:
|
1297
1336
|
final = np.zeros((zsh, ysh, xsh, nb_labels), dtype=np.float32)
|
1298
1337
|
|
1299
|
-
# allocate result array
|
1300
|
-
|
1338
|
+
# allocate final result array
|
1339
|
+
if rank==0:
|
1340
|
+
label = np.zeros((zsh, ysh, xsh), dtype=np.uint8)
|
1301
1341
|
|
1302
1342
|
# predict segmentation block by block
|
1303
1343
|
z_indices = range(0, zsh-bm.z_patch+1, bm.stride_size)
|
1304
1344
|
for j, z in enumerate(z_indices):
|
1305
|
-
|
1345
|
+
# handle len(z_indices) % ngpus != 0
|
1346
|
+
if len(z_indices)-1-j < ngpus:
|
1347
|
+
nprocs = len(z_indices)-j
|
1348
|
+
else:
|
1349
|
+
nprocs = ngpus
|
1350
|
+
if j % ngpus == rank:
|
1306
1351
|
# load blockwise from TIFF
|
1307
1352
|
if load_blockwise:
|
1308
1353
|
img, _, _, _, _, _, _ = load_prediction_data(bm,
|
@@ -1336,8 +1381,11 @@ def predict_segmentation(bm, region_of_interest, channels, normalization_paramet
|
|
1336
1381
|
# number of patches
|
1337
1382
|
nb_patches = len(list_IDs_block)
|
1338
1383
|
|
1339
|
-
# allocate
|
1340
|
-
|
1384
|
+
# allocate block array
|
1385
|
+
if bm.separation:
|
1386
|
+
block_label = np.zeros((bm.z_patch, ysh, xsh), dtype=np.uint8)
|
1387
|
+
else:
|
1388
|
+
block_probs = np.zeros((bm.z_patch, ysh, xsh, nb_labels), dtype=np.float32)
|
1341
1389
|
|
1342
1390
|
# get one batch of image patches
|
1343
1391
|
for step in range(nb_patches//bm.batch_size):
|
@@ -1369,157 +1417,186 @@ def predict_segmentation(bm, region_of_interest, channels, normalization_paramet
|
|
1369
1417
|
if step*bm.batch_size+i < max_i_block:
|
1370
1418
|
if bm.separation:
|
1371
1419
|
patch = np.argmax(Y[i], axis=-1).astype(np.uint8)
|
1372
|
-
|
1420
|
+
block_label[:,l:l+bm.y_patch,m:m+bm.x_patch] += gradient(patch)
|
1373
1421
|
else:
|
1374
|
-
|
1375
|
-
|
1376
|
-
|
1377
|
-
|
1378
|
-
if
|
1379
|
-
|
1380
|
-
|
1381
|
-
|
1382
|
-
|
1383
|
-
|
1384
|
-
|
1385
|
-
|
1386
|
-
if bm.return_probs:
|
1387
|
-
final[z:z+bm.z_patch] = probs
|
1422
|
+
block_probs[:,l:l+bm.y_patch,m:m+bm.x_patch] += Y[i]
|
1423
|
+
|
1424
|
+
# communicate results
|
1425
|
+
if bm.separation:
|
1426
|
+
if rank==0:
|
1427
|
+
label[z:z+bm.z_patch] += block_label
|
1428
|
+
for source in range(1, nprocs):
|
1429
|
+
receivedata = np.empty_like(block_label)
|
1430
|
+
for i in range(bm.z_patch):
|
1431
|
+
comm.Recv([receivedata[i], MPI.BYTE], source=source, tag=i)
|
1432
|
+
block_start = z_indices[j+source]
|
1433
|
+
label[block_start:block_start+bm.z_patch] += receivedata
|
1388
1434
|
else:
|
1389
|
-
|
1390
|
-
|
1391
|
-
|
1392
|
-
|
1393
|
-
|
1394
|
-
|
1395
|
-
|
1396
|
-
|
1397
|
-
|
1398
|
-
|
1399
|
-
|
1400
|
-
|
1401
|
-
|
1402
|
-
|
1403
|
-
|
1404
|
-
|
1405
|
-
|
1406
|
-
|
1407
|
-
|
1408
|
-
|
1409
|
-
|
1410
|
-
|
1411
|
-
|
1412
|
-
|
1413
|
-
|
1414
|
-
|
1415
|
-
|
1416
|
-
|
1417
|
-
|
1418
|
-
|
1419
|
-
|
1420
|
-
|
1421
|
-
|
1422
|
-
|
1435
|
+
for i in range(bm.z_patch):
|
1436
|
+
comm.Send([block_label[i].copy(), MPI.BYTE], dest=0, tag=i)
|
1437
|
+
else:
|
1438
|
+
if rank==0:
|
1439
|
+
for source in range(nprocs):
|
1440
|
+
if source>0:
|
1441
|
+
probs = np.empty_like(block_probs)
|
1442
|
+
for i in range(bm.z_patch):
|
1443
|
+
comm.Recv([probs[i], MPI.FLOAT], source=source, tag=i)
|
1444
|
+
else:
|
1445
|
+
probs = block_probs
|
1446
|
+
|
1447
|
+
# overlap in z direction
|
1448
|
+
if bm.stride_size < bm.z_patch:
|
1449
|
+
if j+source>0:
|
1450
|
+
probs[:bm.stride_size] += overlap
|
1451
|
+
overlap = probs[bm.stride_size:].copy()
|
1452
|
+
|
1453
|
+
# calculate result
|
1454
|
+
block_z = z_indices[j+source]
|
1455
|
+
if j+source==len(z_indices)-1:
|
1456
|
+
label[block_z:block_z+bm.z_patch] = np.argmax(probs, axis=-1).astype(np.uint8)
|
1457
|
+
if bm.return_probs:
|
1458
|
+
final[block_z:block_z+bm.z_patch] = probs
|
1459
|
+
else:
|
1460
|
+
block_zsh = min(bm.stride_size, bm.z_patch)
|
1461
|
+
label[block_z:block_z+block_zsh] = np.argmax(probs[:block_zsh], axis=-1).astype(np.uint8)
|
1462
|
+
if bm.return_probs:
|
1463
|
+
final[block_z:block_z+block_zsh] = probs[:block_zsh]
|
1464
|
+
else:
|
1465
|
+
for i in range(bm.z_patch):
|
1466
|
+
comm.Send([block_probs[i].copy(), MPI.FLOAT], dest=0, tag=i)
|
1467
|
+
if rank==0:
|
1468
|
+
|
1469
|
+
# refine mask data with result
|
1470
|
+
if bm.refinement:
|
1471
|
+
# loop over boundary patches
|
1472
|
+
for i, ID in enumerate(list_IDs):
|
1473
|
+
if i < max_i:
|
1474
|
+
k = ID // (ysh*xsh)
|
1475
|
+
rest = ID % (ysh*xsh)
|
1476
|
+
l = rest // xsh
|
1477
|
+
m = rest % xsh
|
1478
|
+
mask[k:k+bm.z_patch, l:l+bm.y_patch, m:m+bm.x_patch] = label[k:k+bm.z_patch, l:l+bm.y_patch, m:m+bm.x_patch]
|
1479
|
+
label = mask
|
1480
|
+
|
1481
|
+
# remove appendix
|
1482
|
+
if bm.return_probs:
|
1483
|
+
final = final[:-z_rest,:-y_rest,:-x_rest]
|
1484
|
+
label = label[:-z_rest,:-y_rest,:-x_rest]
|
1485
|
+
zsh, ysh, xsh = label.shape
|
1486
|
+
|
1487
|
+
# return probabilities
|
1488
|
+
if bm.return_probs:
|
1489
|
+
counter = np.zeros((zsh, ysh, xsh, nb_labels), dtype=np.float32)
|
1490
|
+
nb = 0
|
1491
|
+
for k in range(0, zsh-bm.z_patch+1, bm.stride_size):
|
1492
|
+
for l in range(0, ysh-bm.y_patch+1, bm.stride_size):
|
1493
|
+
for m in range(0, xsh-bm.x_patch+1, bm.stride_size):
|
1494
|
+
counter[k:k+bm.z_patch, l:l+bm.y_patch, m:m+bm.x_patch] += 1
|
1495
|
+
nb += 1
|
1496
|
+
counter[counter==0] = 1
|
1497
|
+
probabilities = final / counter
|
1498
|
+
if bm.scaling:
|
1499
|
+
probabilities = img_resize(probabilities, z_shape, y_shape, x_shape)
|
1500
|
+
if np.any(region_of_interest):
|
1501
|
+
min_z,max_z,min_y,max_y,min_x,max_x,original_zsh,original_ysh,original_xsh = region_of_interest[:]
|
1502
|
+
tmp = np.zeros((original_zsh, original_ysh, original_xsh, nb_labels), dtype=np.float32)
|
1503
|
+
tmp[min_z:max_z,min_y:max_y,min_x:max_x] = probabilities
|
1504
|
+
probabilities = np.copy(tmp, order='C')
|
1505
|
+
results['probs'] = probabilities
|
1506
|
+
|
1507
|
+
# rescale final to input size
|
1423
1508
|
if bm.scaling:
|
1424
|
-
|
1509
|
+
label = img_resize(label, z_shape, y_shape, x_shape, labels=True)
|
1510
|
+
|
1511
|
+
# revert automatic cropping
|
1425
1512
|
if np.any(region_of_interest):
|
1426
1513
|
min_z,max_z,min_y,max_y,min_x,max_x,original_zsh,original_ysh,original_xsh = region_of_interest[:]
|
1427
|
-
tmp = np.zeros((original_zsh, original_ysh, original_xsh
|
1428
|
-
tmp[min_z:max_z,min_y:max_y,min_x:max_x] =
|
1429
|
-
|
1430
|
-
|
1431
|
-
|
1432
|
-
|
1433
|
-
|
1434
|
-
|
1514
|
+
tmp = np.zeros((original_zsh, original_ysh, original_xsh), dtype=np.uint8)
|
1515
|
+
tmp[min_z:max_z,min_y:max_y,min_x:max_x] = label
|
1516
|
+
label = np.copy(tmp, order='C')
|
1517
|
+
|
1518
|
+
# get result
|
1519
|
+
if not bm.separation:
|
1520
|
+
label = get_labels(label, bm.allLabels)
|
1521
|
+
results['regular'] = label
|
1522
|
+
|
1523
|
+
# load header from file
|
1524
|
+
if bm.header_file and os.path.exists(bm.header_file):
|
1525
|
+
_, bm.header = load_data(bm.header_file)
|
1526
|
+
# update file extension
|
1527
|
+
if bm.header is not None and bm.path_to_image:
|
1528
|
+
bm.extension = os.path.splitext(bm.header_file)[1]
|
1529
|
+
if bm.extension == '.gz':
|
1530
|
+
bm.extension = '.nii.gz'
|
1531
|
+
bm.path_to_final = os.path.splitext(bm.path_to_final)[0] + bm.extension
|
1532
|
+
if bm.django_env and not bm.remote and not bm.tarfile:
|
1533
|
+
bm.path_to_final = unique_file_path(bm.path_to_final)
|
1534
|
+
|
1535
|
+
# handle amira header
|
1536
|
+
if bm.header is not None:
|
1537
|
+
if bm.extension == '.am':
|
1538
|
+
bm.header = set_image_dimensions(bm.header[0], label)
|
1539
|
+
if bm.img_header is not None:
|
1540
|
+
try:
|
1541
|
+
bm.header = set_physical_size(bm.header, bm.img_header[0])
|
1542
|
+
except:
|
1543
|
+
pass
|
1544
|
+
bm.header = [bm.header]
|
1545
|
+
else:
|
1546
|
+
# build new header
|
1547
|
+
if bm.img_header is None:
|
1548
|
+
zsh, ysh, xsh = label.shape
|
1549
|
+
bm.img_header = sitk.Image(xsh, ysh, zsh, bm.header.GetPixelID())
|
1550
|
+
# copy metadata
|
1551
|
+
for key in bm.header.GetMetaDataKeys():
|
1552
|
+
if not (re.match(r'Segment\d+_Extent$', key) or key=='Segmentation_ConversionParameters'):
|
1553
|
+
bm.img_header.SetMetaData(key, bm.header.GetMetaData(key))
|
1554
|
+
bm.header = bm.img_header
|
1555
|
+
results['header'] = bm.header
|
1556
|
+
|
1557
|
+
# save result
|
1558
|
+
if bm.path_to_image:
|
1559
|
+
save_data(bm.path_to_final, label, header=bm.header, compress=bm.compression)
|
1435
1560
|
|
1436
|
-
|
1437
|
-
|
1438
|
-
min_z,max_z,min_y,max_y,min_x,max_x,original_zsh,original_ysh,original_xsh = region_of_interest[:]
|
1439
|
-
tmp = np.zeros((original_zsh, original_ysh, original_xsh), dtype=np.uint8)
|
1440
|
-
tmp[min_z:max_z,min_y:max_y,min_x:max_x] = label
|
1441
|
-
label = np.copy(tmp, order='C')
|
1442
|
-
|
1443
|
-
# get result
|
1444
|
-
if not bm.separation:
|
1445
|
-
label = get_labels(label, bm.allLabels)
|
1446
|
-
results['regular'] = label
|
1447
|
-
|
1448
|
-
# load header from file
|
1449
|
-
if bm.header_file and os.path.exists(bm.header_file):
|
1450
|
-
_, bm.header = load_data(bm.header_file)
|
1451
|
-
# update file extension
|
1452
|
-
if bm.header is not None and bm.path_to_image:
|
1453
|
-
bm.extension = os.path.splitext(bm.header_file)[1]
|
1561
|
+
# paths to optional results
|
1562
|
+
filename, bm.extension = os.path.splitext(bm.path_to_final)
|
1454
1563
|
if bm.extension == '.gz':
|
1455
1564
|
bm.extension = '.nii.gz'
|
1456
|
-
|
1457
|
-
|
1458
|
-
|
1459
|
-
|
1460
|
-
|
1461
|
-
|
1462
|
-
|
1463
|
-
|
1464
|
-
|
1465
|
-
|
1466
|
-
|
1467
|
-
|
1468
|
-
|
1469
|
-
|
1470
|
-
|
1471
|
-
|
1472
|
-
if bm.
|
1473
|
-
|
1474
|
-
|
1475
|
-
|
1476
|
-
|
1477
|
-
|
1478
|
-
|
1479
|
-
|
1480
|
-
|
1481
|
-
|
1482
|
-
|
1483
|
-
|
1484
|
-
|
1485
|
-
|
1486
|
-
|
1487
|
-
|
1488
|
-
|
1489
|
-
|
1490
|
-
|
1491
|
-
|
1492
|
-
|
1493
|
-
path_to_cleaned_filled = filename + '.cleaned.filled' + bm.extension
|
1494
|
-
path_to_refined = filename + '.refined' + bm.extension
|
1495
|
-
path_to_acwe = filename + '.acwe' + bm.extension
|
1496
|
-
|
1497
|
-
# remove outliers
|
1498
|
-
if bm.clean:
|
1499
|
-
cleaned_result = clean(label, bm.clean)
|
1500
|
-
results['cleaned'] = cleaned_result
|
1501
|
-
if bm.path_to_image:
|
1502
|
-
save_data(path_to_cleaned, cleaned_result, header=bm.header, compress=bm.compression)
|
1503
|
-
if bm.fill:
|
1504
|
-
filled_result = clean(label, bm.fill)
|
1505
|
-
results['filled'] = filled_result
|
1506
|
-
if bm.path_to_image:
|
1507
|
-
save_data(path_to_filled, filled_result, header=bm.header, compress=bm.compression)
|
1508
|
-
if bm.clean and bm.fill:
|
1509
|
-
cleaned_filled_result = cleaned_result + (filled_result - label)
|
1510
|
-
results['cleaned_filled'] = cleaned_filled_result
|
1511
|
-
if bm.path_to_image:
|
1512
|
-
save_data(path_to_cleaned_filled, cleaned_filled_result, header=bm.header, compress=bm.compression)
|
1513
|
-
|
1514
|
-
# post-processing with active contour
|
1515
|
-
if bm.acwe:
|
1516
|
-
acwe_result = activeContour(bm.img_data, label, bm.acwe_alpha, bm.acwe_smooth, bm.acwe_steps)
|
1517
|
-
refined_result = activeContour(bm.img_data, label, simple=True)
|
1518
|
-
results['acwe'] = acwe_result
|
1519
|
-
results['refined'] = refined_result
|
1520
|
-
if bm.path_to_image:
|
1521
|
-
save_data(path_to_acwe, acwe_result, header=bm.header, compress=bm.compression)
|
1522
|
-
save_data(path_to_refined, refined_result, header=bm.header, compress=bm.compression)
|
1523
|
-
|
1524
|
-
return results, bm
|
1565
|
+
filename = filename[:-4]
|
1566
|
+
path_to_cleaned = filename + '.cleaned' + bm.extension
|
1567
|
+
path_to_filled = filename + '.filled' + bm.extension
|
1568
|
+
path_to_cleaned_filled = filename + '.cleaned.filled' + bm.extension
|
1569
|
+
path_to_refined = filename + '.refined' + bm.extension
|
1570
|
+
path_to_acwe = filename + '.acwe' + bm.extension
|
1571
|
+
|
1572
|
+
# remove outliers
|
1573
|
+
if bm.clean:
|
1574
|
+
cleaned_result = clean(label, bm.clean)
|
1575
|
+
results['cleaned'] = cleaned_result
|
1576
|
+
if bm.path_to_image:
|
1577
|
+
save_data(path_to_cleaned, cleaned_result, header=bm.header, compress=bm.compression)
|
1578
|
+
if bm.fill:
|
1579
|
+
filled_result = clean(label, bm.fill)
|
1580
|
+
results['filled'] = filled_result
|
1581
|
+
if bm.path_to_image:
|
1582
|
+
save_data(path_to_filled, filled_result, header=bm.header, compress=bm.compression)
|
1583
|
+
if bm.clean and bm.fill:
|
1584
|
+
cleaned_filled_result = cleaned_result + (filled_result - label)
|
1585
|
+
results['cleaned_filled'] = cleaned_filled_result
|
1586
|
+
if bm.path_to_image:
|
1587
|
+
save_data(path_to_cleaned_filled, cleaned_filled_result, header=bm.header, compress=bm.compression)
|
1588
|
+
|
1589
|
+
# post-processing with active contour
|
1590
|
+
if bm.acwe:
|
1591
|
+
acwe_result = activeContour(bm.img_data, label, bm.acwe_alpha, bm.acwe_smooth, bm.acwe_steps)
|
1592
|
+
refined_result = activeContour(bm.img_data, label, simple=True)
|
1593
|
+
results['acwe'] = acwe_result
|
1594
|
+
results['refined'] = refined_result
|
1595
|
+
if bm.path_to_image:
|
1596
|
+
save_data(path_to_acwe, acwe_result, header=bm.header, compress=bm.compression)
|
1597
|
+
save_data(path_to_refined, refined_result, header=bm.header, compress=bm.compression)
|
1598
|
+
|
1599
|
+
return results, bm
|
1600
|
+
else:
|
1601
|
+
return None, None
|
1525
1602
|
|
@@ -1,6 +1,6 @@
|
|
1
|
-
Metadata-Version: 2.
|
1
|
+
Metadata-Version: 2.2
|
2
2
|
Name: biomedisa
|
3
|
-
Version: 24.8.
|
3
|
+
Version: 24.8.8
|
4
4
|
Summary: Segmentation of 3D volumetric image data
|
5
5
|
Author: Philipp Lösel
|
6
6
|
Author-email: philipp.loesel@anu.edu.au
|
@@ -10,7 +10,7 @@ Project-URL: GitHub, https://github.com/biomedisa/biomedisa
|
|
10
10
|
Classifier: Programming Language :: Python :: 3
|
11
11
|
Classifier: License :: OSI Approved :: European Union Public Licence 1.2 (EUPL 1.2)
|
12
12
|
Classifier: Operating System :: OS Independent
|
13
|
-
Requires-Python: >=3.
|
13
|
+
Requires-Python: >=3.10
|
14
14
|
Description-Content-Type: text/markdown
|
15
15
|
License-File: LICENSE
|
16
16
|
|
@@ -19,6 +19,7 @@ License-File: LICENSE
|
|
19
19
|
- [Overview](#overview)
|
20
20
|
- [Hardware Requirements](#hardware-requirements)
|
21
21
|
- [Installation (command-line based)](#installation-command-line-based)
|
22
|
+
- [Installation (3D Slicer extension)](#installation-3d-slicer-extension)
|
22
23
|
- [Installation (browser based)](#installation-browser-based)
|
23
24
|
- [Download Data](#download-data)
|
24
25
|
- [Revisions](#revisions)
|
@@ -33,14 +34,15 @@ License-File: LICENSE
|
|
33
34
|
- [License](#license)
|
34
35
|
|
35
36
|
## Overview
|
36
|
-
Biomedisa (https://biomedisa.info) is a free and easy-to-use open-source application for segmenting large 3D volumetric images such as CT and MRI scans, developed at [The Australian National University CTLab](https://ctlab.anu.edu.au/). Biomedisa's smart interpolation of sparsely pre-segmented slices enables accurate semi-automated segmentation by considering the complete underlying image data. Additionally, Biomedisa enables deep learning for fully automated segmentation across similar samples and structures. It is compatible with segmentation tools like Amira/Avizo, ImageJ/Fiji and 3D Slicer. If you are using Biomedisa or the data for your research please cite: Lösel, P.D. et al. [Introducing Biomedisa as an open-source online platform for biomedical image segmentation.](https://www.nature.com/articles/s41467-020-19303-w) *Nat. Commun.* **11**, 5577 (2020).
|
37
|
+
Biomedisa (https://biomedisa.info) is a free and easy-to-use open-source application for segmenting large 3D volumetric images such as CT and MRI scans, developed at [The Australian National University CTLab](https://ctlab.anu.edu.au/). Biomedisa's smart interpolation of sparsely pre-segmented slices enables accurate semi-automated segmentation by considering the complete underlying image data. Additionally, Biomedisa enables deep learning for fully automated segmentation across similar samples and structures. It is compatible with segmentation tools like Amira/Avizo, ImageJ/Fiji, and 3D Slicer. If you are using Biomedisa or the data for your research please cite: Lösel, P.D. et al. [Introducing Biomedisa as an open-source online platform for biomedical image segmentation.](https://www.nature.com/articles/s41467-020-19303-w) *Nat. Commun.* **11**, 5577 (2020).
|
37
38
|
|
38
39
|
## Hardware Requirements
|
39
|
-
+ One or more NVIDIA GPUs
|
40
|
+
+ One or more NVIDIA GPUs.
|
40
41
|
|
41
42
|
## Installation (command-line based)
|
42
|
-
+ [Ubuntu 22
|
43
|
-
+ [Ubuntu 22
|
43
|
+
+ [Ubuntu 22/24 + Smart Interpolation](https://github.com/biomedisa/biomedisa/blob/master/README/ubuntu_interpolation_cli.md)
|
44
|
+
+ [Ubuntu 22/24 + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/ubuntu_deeplearning_cli.md)
|
45
|
+
+ [Ubuntu 22/24 + Smart Interpolation + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/ubuntu_cli.md)
|
44
46
|
+ [Windows 10/11 + Smart Interpolation + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/windows10_cuda_gpu_cli.md)
|
45
47
|
+ [Windows (WSL) + Smart Interpolation + Deep Learning](https://github.com/biomedisa/biomedisa/blob/master/README/windows_wsl.md)
|
46
48
|
|
@@ -165,7 +167,7 @@ save_data('final.Head5.am', results['regular'], results['header'])
|
|
165
167
|
|
166
168
|
#### Command-line based (prediction)
|
167
169
|
```
|
168
|
-
python -m biomedisa.deeplearning C:\Users\%USERNAME%\Downloads\testing_axial_crop_pat13.nii.gz C:\Users\%USERNAME%\Downloads\heart.h5
|
170
|
+
python -m biomedisa.deeplearning C:\Users\%USERNAME%\Downloads\testing_axial_crop_pat13.nii.gz C:\Users\%USERNAME%\Downloads\heart.h5
|
169
171
|
```
|
170
172
|
|
171
173
|
## Mesh Generator
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
{biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/amira_to_np/amira_data_stream.py
RENAMED
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
{biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/pycuda_large_allx.py
RENAMED
File without changes
|
File without changes
|
{biomedisa-24.8.6 → biomedisa-24.8.8}/src/biomedisa/features/random_walk/pycuda_small_allx.py
RENAMED
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|