megadetector 5.0.29__py3-none-any.whl → 10.0.0__py3-none-any.whl

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.

Potentially problematic release.


This version of megadetector might be problematic. Click here for more details.

Files changed (95) hide show
  1. megadetector/classification/efficientnet/model.py +8 -8
  2. megadetector/classification/efficientnet/utils.py +6 -5
  3. megadetector/classification/prepare_classification_script_mc.py +3 -3
  4. megadetector/data_management/annotations/annotation_constants.py +0 -1
  5. megadetector/data_management/camtrap_dp_to_coco.py +34 -1
  6. megadetector/data_management/cct_json_utils.py +2 -2
  7. megadetector/data_management/coco_to_yolo.py +22 -5
  8. megadetector/data_management/databases/add_width_and_height_to_db.py +85 -12
  9. megadetector/data_management/databases/combine_coco_camera_traps_files.py +2 -2
  10. megadetector/data_management/databases/integrity_check_json_db.py +29 -15
  11. megadetector/data_management/generate_crops_from_cct.py +50 -1
  12. megadetector/data_management/labelme_to_coco.py +4 -2
  13. megadetector/data_management/labelme_to_yolo.py +82 -2
  14. megadetector/data_management/lila/generate_lila_per_image_labels.py +276 -18
  15. megadetector/data_management/lila/get_lila_annotation_counts.py +5 -3
  16. megadetector/data_management/lila/lila_common.py +3 -0
  17. megadetector/data_management/lila/test_lila_metadata_urls.py +15 -5
  18. megadetector/data_management/mewc_to_md.py +5 -0
  19. megadetector/data_management/ocr_tools.py +4 -3
  20. megadetector/data_management/read_exif.py +20 -5
  21. megadetector/data_management/remap_coco_categories.py +66 -4
  22. megadetector/data_management/remove_exif.py +50 -1
  23. megadetector/data_management/rename_images.py +3 -3
  24. megadetector/data_management/resize_coco_dataset.py +563 -95
  25. megadetector/data_management/yolo_output_to_md_output.py +131 -2
  26. megadetector/data_management/yolo_to_coco.py +140 -5
  27. megadetector/detection/change_detection.py +4 -3
  28. megadetector/detection/pytorch_detector.py +60 -22
  29. megadetector/detection/run_detector.py +225 -25
  30. megadetector/detection/run_detector_batch.py +42 -16
  31. megadetector/detection/run_inference_with_yolov5_val.py +12 -2
  32. megadetector/detection/run_tiled_inference.py +1 -0
  33. megadetector/detection/video_utils.py +53 -24
  34. megadetector/postprocessing/add_max_conf.py +4 -0
  35. megadetector/postprocessing/categorize_detections_by_size.py +1 -1
  36. megadetector/postprocessing/classification_postprocessing.py +55 -20
  37. megadetector/postprocessing/combine_batch_outputs.py +3 -2
  38. megadetector/postprocessing/compare_batch_results.py +64 -10
  39. megadetector/postprocessing/convert_output_format.py +12 -8
  40. megadetector/postprocessing/create_crop_folder.py +137 -10
  41. megadetector/postprocessing/load_api_results.py +26 -8
  42. megadetector/postprocessing/md_to_coco.py +4 -4
  43. megadetector/postprocessing/md_to_labelme.py +18 -7
  44. megadetector/postprocessing/merge_detections.py +5 -0
  45. megadetector/postprocessing/postprocess_batch_results.py +6 -3
  46. megadetector/postprocessing/remap_detection_categories.py +55 -2
  47. megadetector/postprocessing/render_detection_confusion_matrix.py +9 -6
  48. megadetector/postprocessing/repeat_detection_elimination/repeat_detections_core.py +2 -2
  49. megadetector/taxonomy_mapping/map_new_lila_datasets.py +3 -4
  50. megadetector/taxonomy_mapping/prepare_lila_taxonomy_release.py +40 -19
  51. megadetector/taxonomy_mapping/preview_lila_taxonomy.py +1 -1
  52. megadetector/taxonomy_mapping/species_lookup.py +123 -41
  53. megadetector/utils/ct_utils.py +133 -113
  54. megadetector/utils/md_tests.py +93 -13
  55. megadetector/utils/path_utils.py +137 -107
  56. megadetector/utils/split_locations_into_train_val.py +2 -2
  57. megadetector/utils/string_utils.py +7 -7
  58. megadetector/utils/url_utils.py +81 -58
  59. megadetector/utils/wi_utils.py +46 -17
  60. megadetector/visualization/plot_utils.py +13 -9
  61. megadetector/visualization/render_images_with_thumbnails.py +2 -1
  62. megadetector/visualization/visualization_utils.py +94 -46
  63. megadetector/visualization/visualize_db.py +36 -9
  64. megadetector/visualization/visualize_detector_output.py +4 -4
  65. {megadetector-5.0.29.dist-info → megadetector-10.0.0.dist-info}/METADATA +135 -135
  66. megadetector-10.0.0.dist-info/RECORD +139 -0
  67. {megadetector-5.0.29.dist-info → megadetector-10.0.0.dist-info}/licenses/LICENSE +0 -0
  68. {megadetector-5.0.29.dist-info → megadetector-10.0.0.dist-info}/top_level.txt +0 -0
  69. megadetector/api/batch_processing/api_core/__init__.py +0 -0
  70. megadetector/api/batch_processing/api_core/batch_service/__init__.py +0 -0
  71. megadetector/api/batch_processing/api_core/batch_service/score.py +0 -438
  72. megadetector/api/batch_processing/api_core/server.py +0 -294
  73. megadetector/api/batch_processing/api_core/server_api_config.py +0 -97
  74. megadetector/api/batch_processing/api_core/server_app_config.py +0 -55
  75. megadetector/api/batch_processing/api_core/server_batch_job_manager.py +0 -220
  76. megadetector/api/batch_processing/api_core/server_job_status_table.py +0 -149
  77. megadetector/api/batch_processing/api_core/server_orchestration.py +0 -360
  78. megadetector/api/batch_processing/api_core/server_utils.py +0 -88
  79. megadetector/api/batch_processing/api_core_support/__init__.py +0 -0
  80. megadetector/api/batch_processing/api_core_support/aggregate_results_manually.py +0 -46
  81. megadetector/api/batch_processing/api_support/__init__.py +0 -0
  82. megadetector/api/batch_processing/api_support/summarize_daily_activity.py +0 -152
  83. megadetector/api/batch_processing/data_preparation/__init__.py +0 -0
  84. megadetector/api/synchronous/__init__.py +0 -0
  85. megadetector/api/synchronous/api_core/animal_detection_api/__init__.py +0 -0
  86. megadetector/api/synchronous/api_core/animal_detection_api/api_backend.py +0 -151
  87. megadetector/api/synchronous/api_core/animal_detection_api/api_frontend.py +0 -263
  88. megadetector/api/synchronous/api_core/animal_detection_api/config.py +0 -35
  89. megadetector/api/synchronous/api_core/tests/__init__.py +0 -0
  90. megadetector/api/synchronous/api_core/tests/load_test.py +0 -109
  91. megadetector/utils/azure_utils.py +0 -178
  92. megadetector/utils/sas_blob_utils.py +0 -513
  93. megadetector-5.0.29.dist-info/RECORD +0 -163
  94. /megadetector/{api/batch_processing/__init__.py → __init__.py} +0 -0
  95. {megadetector-5.0.29.dist-info → megadetector-10.0.0.dist-info}/WHEEL +0 -0
@@ -2,7 +2,9 @@
2
2
 
3
3
  remap_coco_categories.py
4
4
 
5
- Given a COCO-formatted dataset, remap the categories to a new mapping.
5
+ Given a COCO-formatted dataset, remap the categories to a new mapping. A common use
6
+ case is to take a fine-grained dataset (e.g. with species-level categories) and
7
+ map them to coarse categories (typically MD categories).
6
8
 
7
9
  """
8
10
 
@@ -10,6 +12,7 @@ Given a COCO-formatted dataset, remap the categories to a new mapping.
10
12
 
11
13
  import os
12
14
  import json
15
+ import argparse
13
16
 
14
17
  from copy import deepcopy
15
18
  from megadetector.utils.ct_utils import invert_dictionary
@@ -29,9 +32,9 @@ def remap_coco_categories(input_data,
29
32
  Args:
30
33
  input_data (str or dict): a COCO-formatted dict or a filename. If it's a dict, it will
31
34
  be copied, not modified in place.
32
- output_category_name_to_id (dict) a dict mapping strings to ints. Categories not in
35
+ output_category_name_to_id (dict): a dict mapping strings to ints. Categories not in
33
36
  this dict will be ignored or will result in errors, depending on allow_unused_categories.
34
- input_category_name_to_output_category_name: a dict mapping strings to strings.
37
+ input_category_name_to_output_category_name (dict): a dict mapping strings to strings.
35
38
  Annotations using categories not in this dict will be omitted or will result in
36
39
  errors, depending on allow_unused_categories.
37
40
  output_file (str, optional): output file to which we should write remapped COCO data
@@ -130,4 +133,63 @@ def remap_coco_categories(input_data,
130
133
 
131
134
  #%% Command-line driver
132
135
 
133
- # TODO
136
+ def main():
137
+ """
138
+ Command-line interface to remap COCO categories.
139
+ """
140
+
141
+ parser = argparse.ArgumentParser(
142
+ description='Remap categories in a COCO-formatted dataset'
143
+ )
144
+ parser.add_argument(
145
+ 'input_coco_file',
146
+ type=str,
147
+ help='Path to the input COCO .json file'
148
+ )
149
+ parser.add_argument(
150
+ 'output_category_map_file',
151
+ type=str,
152
+ help="Path to a .json file mapping output category names to integer IDs (e.g., {'cat':0, 'dog':1})"
153
+ )
154
+ parser.add_argument(
155
+ 'input_to_output_category_map_file',
156
+ type=str,
157
+ help="Path to a .json file mapping input category names to output category names" + \
158
+ " (e.g., {'old_cat_name':'cat', 'old_dog_name':'dog'})"
159
+ )
160
+ parser.add_argument(
161
+ 'output_coco_file',
162
+ type=str,
163
+ help='Path to save the remapped COCO .json file'
164
+ )
165
+ parser.add_argument(
166
+ '--allow_unused_categories',
167
+ action='store_true',
168
+ help='Allow unmapped categories (by default, errors on unmapped categories)'
169
+ )
170
+
171
+ args = parser.parse_args()
172
+
173
+ # Load category mappings
174
+ with open(args.output_category_map_file, 'r') as f:
175
+ output_category_name_to_id = json.load(f)
176
+
177
+ with open(args.input_to_output_category_map_file, 'r') as f:
178
+ input_category_name_to_output_category_name = json.load(f)
179
+
180
+ # Load COCO data
181
+ with open(args.input_coco_file, 'r') as f:
182
+ input_data = json.load(f)
183
+
184
+ remap_coco_categories(
185
+ input_data=input_data,
186
+ output_category_name_to_id=output_category_name_to_id,
187
+ input_category_name_to_output_category_name=input_category_name_to_output_category_name,
188
+ output_file=args.output_coco_file,
189
+ allow_unused_categories=args.allow_unused_categories
190
+ )
191
+
192
+ print(f'Successfully remapped categories and saved to {args.output_coco_file}')
193
+
194
+ if __name__ == '__main__':
195
+ main()
@@ -14,6 +14,7 @@ included in package-level dependency lists. YMMV.
14
14
 
15
15
  import os
16
16
  import glob
17
+ import argparse
17
18
 
18
19
  from multiprocessing.pool import Pool as Pool
19
20
  from tqdm import tqdm
@@ -28,6 +29,12 @@ def remove_exif_from_image(fn):
28
29
  pyexiv2 is not thread safe, do not call this function in parallel within a process.
29
30
 
30
31
  Parallelizing across processes is fine.
32
+
33
+ Args:
34
+ fn (str): image file from which we should remove EXIF information
35
+
36
+ Returns:
37
+ bool: whether EXIF removal succeeded
31
38
  """
32
39
 
33
40
  import pyexiv2 # type: ignore
@@ -40,6 +47,7 @@ def remove_exif_from_image(fn):
40
47
  img.close()
41
48
  except Exception as e:
42
49
  print('EXIF error on {}: {}'.format(fn,str(e)))
50
+ return False
43
51
 
44
52
  return True
45
53
 
@@ -99,4 +107,45 @@ def remove_exif(image_base_folder,recursive=True,n_processes=1):
99
107
 
100
108
  #%% Command-line driver
101
109
 
102
- ## TODO
110
+ def main():
111
+ """
112
+ Command-line interface to remove EXIF data from images.
113
+ """
114
+
115
+ parser = argparse.ArgumentParser(
116
+ description='Removes EXIF/IPTC/XMP metadata from images in a folder'
117
+ )
118
+ parser.add_argument(
119
+ 'image_base_folder',
120
+ type=str,
121
+ help='Folder to process for EXIF removal'
122
+ )
123
+ parser.add_argument(
124
+ '--nonrecursive',
125
+ action='store_true',
126
+ help="Don't recurse into [image_base_folder] (default is recursive)"
127
+ )
128
+ parser.add_argument(
129
+ '--n_processes',
130
+ type=int,
131
+ default=1,
132
+ help='Number of concurrent processes for EXIF removal (default: 1)'
133
+ )
134
+
135
+ args = parser.parse_args()
136
+
137
+ recursive = (not args.nonrecursive)
138
+
139
+ print('Processing folder: {}'.format(args.image_base_folder))
140
+ if not os.path.isdir(args.image_base_folder):
141
+ raise ValueError('Folder not found at {}'.format(args.image_base_folder))
142
+
143
+ remove_exif(
144
+ image_base_folder=args.image_base_folder,
145
+ recursive=recursive,
146
+ n_processes=args.n_processes
147
+ )
148
+ print('Finished removing EXIF data')
149
+
150
+ if __name__ == '__main__':
151
+ main()
@@ -32,10 +32,10 @@ def rename_images(input_folder,
32
32
  detections into labelme format.
33
33
 
34
34
  Args:
35
- input_folder: the folder to search for images, always recursive
36
- output_folder: the folder to which we will copy images; cannot be the
35
+ input_folder (str): the folder to search for images, always recursive
36
+ output_folder (str): the folder to which we will copy images; cannot be the
37
37
  same as [input_folder]
38
- dry_run: only map images, don't actually copy
38
+ dry_run (bool, optional): only map images, don't actually copy
39
39
  verbose (bool, optional): enable additional debug output
40
40
  read_exif_options (ReadExifOptions, optional): parameters controlling the reading of
41
41
  EXIF information