deepdoctection 0.39.5__tar.gz → 0.39.7__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.
Potentially problematic release.
This version of deepdoctection might be problematic. Click here for more details.
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/PKG-INFO +3 -2
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/__init__.py +1 -1
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datapoint/box.py +239 -92
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datapoint/convert.py +4 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datapoint/view.py +1 -1
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/registry.py +5 -2
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/sub_layout.py +1 -1
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/train/hf_detr_train.py +40 -8
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/train/hf_layoutlm_train.py +2 -2
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/types.py +1 -1
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection.egg-info/PKG-INFO +3 -2
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/LICENSE +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/README.md +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/analyzer/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/analyzer/_config.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/analyzer/dd.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/analyzer/factory.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/configs/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/configs/conf_dd_one.yaml +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/configs/conf_tesseract.yaml +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/dataflow/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/dataflow/base.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/dataflow/common.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/dataflow/custom.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/dataflow/custom_serialize.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/dataflow/parallel_map.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/dataflow/serialize.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/dataflow/stats.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datapoint/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datapoint/annotation.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datapoint/image.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/adapter.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/base.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/dataflow_builder.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/info.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/doclaynet.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/fintabnet.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/funsd.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/iiitar13k.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/layouttest.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/publaynet.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/pubtables1m.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/pubtabnet.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/rvlcdip.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/xfund.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/xsl/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/instances/xsl/pascal_voc.xsl +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/datasets/save.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/eval/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/eval/accmetric.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/eval/base.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/eval/cocometric.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/eval/eval.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/eval/registry.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/eval/tedsmetric.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/eval/tp_eval_callback.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/base.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/d2detect.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/deskew.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/doctrocr.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/fastlang.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/hfdetr.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/hflayoutlm.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/hflm.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/model.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/pdftext.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/pt/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/pt/nms.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/pt/ptutils.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tessocr.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/texocr.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tfutils.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpcompat.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/common.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/config/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/config/config.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/modeling/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/modeling/backbone.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/modeling/generalized_rcnn.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/modeling/model_box.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/modeling/model_cascade.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/modeling/model_fpn.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/modeling/model_frcnn.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/modeling/model_mrcnn.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/modeling/model_rpn.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/predict.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/preproc.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/utils/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/utils/box_ops.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tp/tpfrcnn/utils/np_box_ops.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/extern/tpdetect.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/cats.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/cocostruct.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/d2struct.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/hfstruct.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/laylmstruct.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/maputils.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/match.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/misc.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/pascalstruct.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/prodigystruct.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/pubstruct.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/tpstruct.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/mapper/xfundstruct.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/anngen.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/base.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/common.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/concurrency.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/doctectionpipe.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/language.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/layout.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/lm.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/order.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/refine.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/registry.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/segment.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/text.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/pipe/transform.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/py.typed +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/train/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/train/d2_frcnn_train.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/train/tp_frcnn_train.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/__init__.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/concurrency.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/context.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/develop.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/env_info.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/error.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/file_utils.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/fs.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/identifier.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/logger.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/metacfg.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/mocks.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/pdf_utils.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/settings.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/tqdm.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/transform.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/utils.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection/utils/viz.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection.egg-info/SOURCES.txt +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection.egg-info/dependency_links.txt +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection.egg-info/requires.txt +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/deepdoctection.egg-info/top_level.txt +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/setup.cfg +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/setup.py +0 -0
- {deepdoctection-0.39.5 → deepdoctection-0.39.7}/tests/test_utils.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
Metadata-Version: 2.
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
2
|
Name: deepdoctection
|
|
3
|
-
Version: 0.39.
|
|
3
|
+
Version: 0.39.7
|
|
4
4
|
Summary: Repository for Document AI
|
|
5
5
|
Home-page: https://github.com/deepdoctection/deepdoctection
|
|
6
6
|
Author: Dr. Janis Meyer
|
|
@@ -133,6 +133,7 @@ Dynamic: description
|
|
|
133
133
|
Dynamic: description-content-type
|
|
134
134
|
Dynamic: home-page
|
|
135
135
|
Dynamic: license
|
|
136
|
+
Dynamic: license-file
|
|
136
137
|
Dynamic: provides-extra
|
|
137
138
|
Dynamic: requires-dist
|
|
138
139
|
Dynamic: requires-python
|
|
@@ -18,10 +18,11 @@
|
|
|
18
18
|
"""
|
|
19
19
|
Implementation of BoundingBox class and related methods
|
|
20
20
|
"""
|
|
21
|
+
from __future__ import annotations
|
|
21
22
|
|
|
22
23
|
from dataclasses import dataclass
|
|
23
24
|
from math import ceil, floor
|
|
24
|
-
from typing import Optional, Sequence, no_type_check
|
|
25
|
+
from typing import Optional, Sequence, Union, no_type_check
|
|
25
26
|
|
|
26
27
|
import numpy as np
|
|
27
28
|
import numpy.typing as npt
|
|
@@ -31,7 +32,7 @@ from numpy import float32
|
|
|
31
32
|
from ..utils.error import BoundingBoxError
|
|
32
33
|
from ..utils.file_utils import cocotools_available
|
|
33
34
|
from ..utils.logger import LoggingRecord, logger
|
|
34
|
-
from ..utils.types import PixelValues
|
|
35
|
+
from ..utils.types import BoxCoordinate, PixelValues
|
|
35
36
|
|
|
36
37
|
with try_import() as import_guard:
|
|
37
38
|
import pycocotools.mask as coco_mask
|
|
@@ -142,96 +143,213 @@ def iou(boxes1: npt.NDArray[float32], boxes2: npt.NDArray[float32]) -> npt.NDArr
|
|
|
142
143
|
return np_iou(boxes1, boxes2)
|
|
143
144
|
|
|
144
145
|
|
|
146
|
+
RELATIVE_COORD_CONVERTER = 10**8
|
|
147
|
+
|
|
148
|
+
|
|
145
149
|
@dataclass
|
|
146
150
|
class BoundingBox:
|
|
147
151
|
"""
|
|
148
|
-
Rectangular bounding box
|
|
149
|
-
representations. You can define an instance by passing the upper left point along with either height
|
|
150
|
-
and width or along with the lower right point. Pass absolute_coords = 'True' if you work with image
|
|
151
|
-
pixel coordinates. If you work with coordinates in the range between (0,1) then pass absolute_coords
|
|
152
|
-
='False'. A bounding box is a disposable object. Do not change the coordinates once the have been set but define
|
|
153
|
-
a new box.
|
|
154
|
-
|
|
155
|
-
`absolute_coords` indicates, whether given coordinates are in absolute or in relative terms
|
|
156
|
-
|
|
157
|
-
`ulx`: upper left x
|
|
152
|
+
Rectangular bounding box that stores coordinates and allows different representations.
|
|
158
153
|
|
|
159
|
-
|
|
154
|
+
This implementation differs from the previous version by using internal integer storage with precision scaling
|
|
155
|
+
for both absolute and relative coordinates. Coordinates are stored internally as integers (_ulx, _uly, etc.)
|
|
156
|
+
with relative coordinates multiplied by RELATIVE_COORD_CONVERTER (10^8) for precision. Properties (ulx, uly, etc.)
|
|
157
|
+
handle the conversion between internal storage and exposed values.
|
|
160
158
|
|
|
161
|
-
|
|
159
|
+
You can define an instance by passing:
|
|
160
|
+
- Upper left point (ulx, uly) + width and height, OR
|
|
161
|
+
- Upper left point (ulx, uly) + lower right point (lrx, lry)
|
|
162
162
|
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
`width`: width
|
|
163
|
+
Notes:
|
|
164
|
+
- When absolute_coords=True, coordinates will be rounded to integers
|
|
165
|
+
- When absolute_coords=False, coordinates must be between 0 and 1
|
|
166
|
+
- The box is validated on initialization to ensure coordinates are valid
|
|
168
167
|
"""
|
|
169
168
|
|
|
170
169
|
absolute_coords: bool
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
170
|
+
_ulx: int = 0
|
|
171
|
+
_uly: int = 0
|
|
172
|
+
_lrx: int = 0
|
|
173
|
+
_lry: int = 0
|
|
174
|
+
_height: int = 0
|
|
175
|
+
_width: int = 0
|
|
176
|
+
|
|
177
|
+
def __init__(
|
|
178
|
+
self,
|
|
179
|
+
absolute_coords: bool,
|
|
180
|
+
ulx: BoxCoordinate,
|
|
181
|
+
uly: BoxCoordinate,
|
|
182
|
+
lrx: BoxCoordinate = 0,
|
|
183
|
+
lry: BoxCoordinate = 0,
|
|
184
|
+
width: BoxCoordinate = 0,
|
|
185
|
+
height: BoxCoordinate = 0,
|
|
186
|
+
):
|
|
187
|
+
"""
|
|
188
|
+
Initialize a BoundingBox instance with the specified coordinates.
|
|
189
|
+
|
|
190
|
+
This initializer supports two ways of defining a bounding box:
|
|
191
|
+
1. Using upper-left coordinates (ulx, uly) with width and height
|
|
192
|
+
2. Using upper-left (ulx, uly) and lower-right (lrx, lry) coordinates
|
|
193
|
+
|
|
194
|
+
When absolute_coords is True, coordinates are stored as integers.
|
|
195
|
+
When absolute_coords is False, coordinates are stored as scaled integers
|
|
196
|
+
(original float values * RELATIVE_COORD_CONVERTER) for precision.
|
|
197
|
+
|
|
198
|
+
:param absolute_coords: Whether coordinates are absolute pixels (True) or normalized [0,1] values (False)
|
|
199
|
+
:param ulx: Upper-left x-coordinate (float or int)
|
|
200
|
+
:param uly: Upper-left y-coordinate (float or int)
|
|
201
|
+
:param lrx: Lower-right x-coordinate (float or int), default 0
|
|
202
|
+
:param lry: Lower-right y-coordinate (float or int), default 0
|
|
203
|
+
:param width: Width of the bounding box (float or int), default 0
|
|
204
|
+
:param height: Height of the bounding box (float or int), default 0
|
|
205
|
+
"""
|
|
206
|
+
self.absolute_coords = absolute_coords
|
|
207
|
+
if absolute_coords:
|
|
208
|
+
self._ulx = round(ulx)
|
|
209
|
+
self._uly = round(uly)
|
|
210
|
+
if lrx and lry:
|
|
211
|
+
self._lrx = round(lrx)
|
|
212
|
+
self._lry = round(lry)
|
|
213
|
+
if width and height:
|
|
214
|
+
self._width = round(width)
|
|
215
|
+
self._height = round(height)
|
|
216
|
+
else:
|
|
217
|
+
self._ulx = round(ulx * RELATIVE_COORD_CONVERTER)
|
|
218
|
+
self._uly = round(uly * RELATIVE_COORD_CONVERTER)
|
|
219
|
+
if lrx and lry:
|
|
220
|
+
self._lrx = round(lrx * RELATIVE_COORD_CONVERTER)
|
|
221
|
+
self._lry = round(lry * RELATIVE_COORD_CONVERTER)
|
|
222
|
+
if width and height:
|
|
223
|
+
self._width = round(width * RELATIVE_COORD_CONVERTER)
|
|
224
|
+
self._height = round(height * RELATIVE_COORD_CONVERTER)
|
|
225
|
+
if not self._width and not self._height:
|
|
226
|
+
self._width = self._lrx - self._ulx
|
|
227
|
+
self._height = self._lry - self._uly
|
|
228
|
+
if not self._lrx and not self._lry:
|
|
229
|
+
self._lrx = self._ulx + self._width
|
|
230
|
+
self._lry = self._uly + self._height
|
|
231
|
+
self.__post_init__()
|
|
177
232
|
|
|
178
233
|
def __post_init__(self) -> None:
|
|
179
|
-
if self.
|
|
180
|
-
if self.
|
|
234
|
+
if self._width == 0:
|
|
235
|
+
if self._lrx is None:
|
|
181
236
|
raise BoundingBoxError("Bounding box not fully initialized")
|
|
182
|
-
self.
|
|
183
|
-
if self.
|
|
184
|
-
if self.
|
|
237
|
+
self._width = self._lrx - self._ulx
|
|
238
|
+
if self._height == 0:
|
|
239
|
+
if self._lry is None:
|
|
185
240
|
raise BoundingBoxError("Bounding box not fully initialized")
|
|
186
|
-
self.
|
|
241
|
+
self._height = self._lry - self._uly
|
|
187
242
|
|
|
188
|
-
if self.
|
|
189
|
-
if self.
|
|
243
|
+
if self._lrx == 0:
|
|
244
|
+
if self._width is None:
|
|
190
245
|
raise BoundingBoxError("Bounding box not fully initialized")
|
|
191
|
-
self.
|
|
192
|
-
if self.
|
|
193
|
-
if self.
|
|
246
|
+
self._lrx = self._ulx + self._width
|
|
247
|
+
if self._lry == 0:
|
|
248
|
+
if self._height is None:
|
|
194
249
|
raise BoundingBoxError("Bounding box not fully initialized")
|
|
195
|
-
self.
|
|
250
|
+
self._lry = self._uly + self._height
|
|
196
251
|
|
|
197
|
-
if not (self.
|
|
198
|
-
raise BoundingBoxError("Bounding box ul must be >= (0
|
|
199
|
-
if not (self.
|
|
252
|
+
if not (self._ulx >= 0 and self._uly >= 0):
|
|
253
|
+
raise BoundingBoxError("Bounding box ul must be >= (0,0)")
|
|
254
|
+
if not (self._height > 0 and self._width > 0):
|
|
200
255
|
raise BoundingBoxError(
|
|
201
256
|
f"bounding box must have height and width >0. Check coords "
|
|
202
257
|
f"ulx: {self.ulx}, uly: {self.uly}, lrx: {self.lrx}, "
|
|
203
258
|
f"lry: {self.lry}."
|
|
204
259
|
)
|
|
205
|
-
if not self.absolute_coords
|
|
206
|
-
|
|
207
|
-
|
|
260
|
+
if not self.absolute_coords and not (
|
|
261
|
+
0 <= self.ulx <= 1 and 0 <= self.uly <= 1 and 0 <= self.lrx <= 1 and 0 <= self.lry <= 1
|
|
262
|
+
):
|
|
263
|
+
raise BoundingBoxError("coordinates must be between 0 and 1")
|
|
208
264
|
|
|
209
265
|
@property
|
|
210
|
-
def
|
|
211
|
-
"""
|
|
212
|
-
|
|
213
|
-
|
|
266
|
+
def ulx(self) -> BoxCoordinate:
|
|
267
|
+
"""ulx property"""
|
|
268
|
+
return self._ulx / RELATIVE_COORD_CONVERTER if not self.absolute_coords else self._ulx
|
|
269
|
+
|
|
270
|
+
@ulx.setter
|
|
271
|
+
def ulx(self, value: BoxCoordinate) -> None:
|
|
272
|
+
"""ulx setter"""
|
|
273
|
+
self._ulx = round(value * RELATIVE_COORD_CONVERTER) if not self.absolute_coords else round(value)
|
|
274
|
+
self._width = self._lrx - self._ulx
|
|
275
|
+
|
|
276
|
+
@property
|
|
277
|
+
def uly(self) -> BoxCoordinate:
|
|
278
|
+
"""uly property"""
|
|
279
|
+
return self._uly / RELATIVE_COORD_CONVERTER if not self.absolute_coords else self._uly
|
|
280
|
+
|
|
281
|
+
@uly.setter
|
|
282
|
+
def uly(self, value: BoxCoordinate) -> None:
|
|
283
|
+
"""uly setter"""
|
|
284
|
+
self._uly = round(value * RELATIVE_COORD_CONVERTER) if not self.absolute_coords else round(value)
|
|
285
|
+
self._height = self._lry - self._uly
|
|
286
|
+
|
|
287
|
+
@property
|
|
288
|
+
def lrx(self) -> BoxCoordinate:
|
|
289
|
+
"""lrx property"""
|
|
290
|
+
return self._lrx / RELATIVE_COORD_CONVERTER if not self.absolute_coords else self._lrx
|
|
291
|
+
|
|
292
|
+
@lrx.setter
|
|
293
|
+
def lrx(self, value: BoxCoordinate) -> None:
|
|
294
|
+
"""lrx setter"""
|
|
295
|
+
self._lrx = round(value * RELATIVE_COORD_CONVERTER) if not self.absolute_coords else round(value)
|
|
296
|
+
self._width = self._lrx - self._ulx
|
|
297
|
+
|
|
298
|
+
@property
|
|
299
|
+
def lry(self) -> BoxCoordinate:
|
|
300
|
+
"""lry property"""
|
|
301
|
+
return self._lry / RELATIVE_COORD_CONVERTER if not self.absolute_coords else self._lry
|
|
302
|
+
|
|
303
|
+
@lry.setter
|
|
304
|
+
def lry(self, value: BoxCoordinate) -> None:
|
|
305
|
+
"""lry setter"""
|
|
306
|
+
self._lry = round(value * RELATIVE_COORD_CONVERTER) if not self.absolute_coords else round(value)
|
|
307
|
+
self._height = self._lry - self._uly
|
|
308
|
+
|
|
309
|
+
@property
|
|
310
|
+
def width(self) -> BoxCoordinate:
|
|
311
|
+
"""width property"""
|
|
312
|
+
return self._width / RELATIVE_COORD_CONVERTER if not self.absolute_coords else self._width
|
|
313
|
+
|
|
314
|
+
@width.setter
|
|
315
|
+
def width(self, value: BoxCoordinate) -> None:
|
|
316
|
+
"""width setter"""
|
|
317
|
+
self._width = round(value * RELATIVE_COORD_CONVERTER) if not self.absolute_coords else round(value)
|
|
318
|
+
self._lrx = self._ulx + self._width
|
|
319
|
+
|
|
320
|
+
@property
|
|
321
|
+
def height(self) -> BoxCoordinate:
|
|
322
|
+
"""height property"""
|
|
323
|
+
return self._height / RELATIVE_COORD_CONVERTER if not self.absolute_coords else self._height
|
|
324
|
+
|
|
325
|
+
@height.setter
|
|
326
|
+
def height(self, value: BoxCoordinate) -> None:
|
|
327
|
+
"""height setter"""
|
|
328
|
+
self._height = round(value * RELATIVE_COORD_CONVERTER) if not self.absolute_coords else round(value)
|
|
329
|
+
self._lry = self._uly + self._height
|
|
330
|
+
|
|
331
|
+
@property
|
|
332
|
+
def cx(self) -> BoxCoordinate:
|
|
333
|
+
"""cx property"""
|
|
334
|
+
if self.absolute_coords:
|
|
335
|
+
return round(self.ulx + 0.5 * self.width)
|
|
214
336
|
return self.ulx + 0.5 * self.width
|
|
215
337
|
|
|
216
338
|
@property
|
|
217
|
-
def cy(self) ->
|
|
218
|
-
"""
|
|
219
|
-
|
|
220
|
-
|
|
339
|
+
def cy(self) -> BoxCoordinate:
|
|
340
|
+
"""cy property"""
|
|
341
|
+
if self.absolute_coords:
|
|
342
|
+
return round(self.uly + 0.5 * self.height)
|
|
221
343
|
return self.uly + 0.5 * self.height
|
|
222
344
|
|
|
223
345
|
@property
|
|
224
|
-
def center(self) ->
|
|
225
|
-
"""
|
|
226
|
-
|
|
227
|
-
"""
|
|
228
|
-
return [self.cx, self.cy]
|
|
346
|
+
def center(self) -> tuple[BoxCoordinate, BoxCoordinate]:
|
|
347
|
+
"""center property"""
|
|
348
|
+
return (self.cx, self.cy)
|
|
229
349
|
|
|
230
350
|
@property
|
|
231
|
-
def area(self) -> float:
|
|
232
|
-
"""
|
|
233
|
-
Bounding box area
|
|
234
|
-
"""
|
|
351
|
+
def area(self) -> Union[int, float]:
|
|
352
|
+
"""area property"""
|
|
235
353
|
if self.absolute_coords:
|
|
236
354
|
return self.width * self.height
|
|
237
355
|
raise ValueError("Cannot calculate area, when bounding box coords are relative")
|
|
@@ -264,7 +382,7 @@ class BoundingBox:
|
|
|
264
382
|
* np_poly_scale
|
|
265
383
|
)
|
|
266
384
|
|
|
267
|
-
def to_list(self, mode: str, scale_x: float = 1.0, scale_y: float = 1.0) -> list[
|
|
385
|
+
def to_list(self, mode: str, scale_x: float = 1.0, scale_y: float = 1.0) -> list[BoxCoordinate]:
|
|
268
386
|
"""
|
|
269
387
|
Returns the coordinates as list
|
|
270
388
|
|
|
@@ -280,36 +398,62 @@ class BoundingBox:
|
|
|
280
398
|
"""
|
|
281
399
|
assert mode in ("xyxy", "xywh", "poly"), "Not a valid mode"
|
|
282
400
|
if mode == "xyxy":
|
|
283
|
-
return
|
|
401
|
+
return (
|
|
402
|
+
[
|
|
403
|
+
round(self.ulx * scale_x),
|
|
404
|
+
round(self.uly * scale_y),
|
|
405
|
+
round(self.lrx * scale_x),
|
|
406
|
+
round(self.lry * scale_y),
|
|
407
|
+
]
|
|
408
|
+
if self.absolute_coords
|
|
409
|
+
else [
|
|
410
|
+
self.ulx * scale_x,
|
|
411
|
+
self.uly * scale_y,
|
|
412
|
+
self.lrx * scale_x,
|
|
413
|
+
self.lry * scale_y,
|
|
414
|
+
]
|
|
415
|
+
)
|
|
416
|
+
if mode == "xywh":
|
|
417
|
+
return (
|
|
418
|
+
[
|
|
419
|
+
round(self.ulx * scale_x),
|
|
420
|
+
round(self.uly * scale_y),
|
|
421
|
+
round(self.width * scale_x),
|
|
422
|
+
round(self.height * scale_y),
|
|
423
|
+
]
|
|
424
|
+
if self.absolute_coords
|
|
425
|
+
else [self.ulx * scale_x, self.uly * scale_y, self.width * scale_x, self.height * scale_y]
|
|
426
|
+
)
|
|
427
|
+
return (
|
|
428
|
+
[
|
|
429
|
+
round(self.ulx * scale_x),
|
|
430
|
+
round(self.uly * scale_y),
|
|
431
|
+
round(self.lrx * scale_x),
|
|
432
|
+
round(self.uly * scale_y),
|
|
433
|
+
round(self.lrx * scale_x),
|
|
434
|
+
round(self.lry * scale_y),
|
|
435
|
+
round(self.ulx * scale_x),
|
|
436
|
+
round(self.lry * scale_y),
|
|
437
|
+
]
|
|
438
|
+
if self.absolute_coords
|
|
439
|
+
else [
|
|
284
440
|
self.ulx * scale_x,
|
|
285
441
|
self.uly * scale_y,
|
|
286
442
|
self.lrx * scale_x,
|
|
443
|
+
self.uly * scale_y,
|
|
444
|
+
self.lrx * scale_x,
|
|
287
445
|
self.lry * scale_y,
|
|
288
|
-
]
|
|
289
|
-
if mode == "xywh":
|
|
290
|
-
return [
|
|
291
446
|
self.ulx * scale_x,
|
|
292
|
-
self.
|
|
293
|
-
self.width * scale_x,
|
|
294
|
-
self.height * scale_y,
|
|
447
|
+
self.lry * scale_y,
|
|
295
448
|
]
|
|
296
|
-
|
|
297
|
-
self.ulx * scale_x,
|
|
298
|
-
self.uly * scale_y,
|
|
299
|
-
self.lrx * scale_x,
|
|
300
|
-
self.uly * scale_y,
|
|
301
|
-
self.lrx * scale_x,
|
|
302
|
-
self.lry * scale_y,
|
|
303
|
-
self.ulx * scale_x,
|
|
304
|
-
self.lry * scale_y,
|
|
305
|
-
]
|
|
449
|
+
)
|
|
306
450
|
|
|
307
451
|
def transform(
|
|
308
452
|
self,
|
|
309
453
|
image_width: float,
|
|
310
454
|
image_height: float,
|
|
311
455
|
absolute_coords: bool = False,
|
|
312
|
-
) ->
|
|
456
|
+
) -> BoundingBox:
|
|
313
457
|
"""
|
|
314
458
|
Transforms bounding box coordinates into absolute or relative coords. Internally, a new bounding box will be
|
|
315
459
|
created. Changing coordinates requires width and height of the whole image.
|
|
@@ -320,8 +464,7 @@ class BoundingBox:
|
|
|
320
464
|
|
|
321
465
|
:return: Either a list or np.array.
|
|
322
466
|
"""
|
|
323
|
-
|
|
324
|
-
if absolute_coords != self.absolute_coords: # only transforming in this case
|
|
467
|
+
if absolute_coords != self.absolute_coords:
|
|
325
468
|
if self.absolute_coords:
|
|
326
469
|
transformed_box = BoundingBox(
|
|
327
470
|
absolute_coords=not self.absolute_coords,
|
|
@@ -344,22 +487,26 @@ class BoundingBox:
|
|
|
344
487
|
def __str__(self) -> str:
|
|
345
488
|
return f"Bounding Box ulx: {self.ulx}, uly: {self.uly}, lrx: {self.lrx}, lry: {self.lry}"
|
|
346
489
|
|
|
490
|
+
def __repr__(self) -> str:
|
|
491
|
+
return (
|
|
492
|
+
f"BoundingBox(absolute_coords={self.absolute_coords}, ulx={self.ulx}, uly={self.uly}, lrx={self.lrx},"
|
|
493
|
+
f" lry={self.lry}, width={self.width}, height={self.height})"
|
|
494
|
+
)
|
|
495
|
+
|
|
347
496
|
@staticmethod
|
|
348
497
|
def remove_keys() -> list[str]:
|
|
349
|
-
"""
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
498
|
+
"""Removing keys when converting the dataclass object to a dict"""
|
|
499
|
+
return ["_height", "_width"]
|
|
500
|
+
|
|
501
|
+
@staticmethod
|
|
502
|
+
def replace_keys() -> dict[str, str]:
|
|
503
|
+
"""Replacing keys when converting the dataclass object to a dict. Useful for backward compatibility"""
|
|
504
|
+
return {"_ulx": "ulx", "_uly": "uly", "_lrx": "lrx", "_lry": "lry"}
|
|
353
505
|
|
|
354
506
|
@classmethod
|
|
355
507
|
@no_type_check
|
|
356
|
-
def from_dict(cls, **kwargs) ->
|
|
357
|
-
"""
|
|
358
|
-
Create `BoundingBox` instance from dict
|
|
359
|
-
|
|
360
|
-
:param kwargs: dict with `BoundingBox` attributes
|
|
361
|
-
:return: Initialized BoundingBox
|
|
362
|
-
"""
|
|
508
|
+
def from_dict(cls, **kwargs) -> BoundingBox:
|
|
509
|
+
"""from dict"""
|
|
363
510
|
return cls(**kwargs)
|
|
364
511
|
|
|
365
512
|
|
|
@@ -65,6 +65,10 @@ def as_dict(obj: Any, dict_factory) -> Union[Any]: # type: ignore
|
|
|
65
65
|
if hasattr(obj, "remove_keys"):
|
|
66
66
|
if attribute.name in obj.remove_keys():
|
|
67
67
|
continue
|
|
68
|
+
if hasattr(obj, "replace_keys"):
|
|
69
|
+
old_to_new_keys = obj.replace_keys()
|
|
70
|
+
if attribute.name in old_to_new_keys:
|
|
71
|
+
attribute.name = obj.replace_keys()[attribute.name]
|
|
68
72
|
result.append((attribute.name, value))
|
|
69
73
|
return dict_factory(result)
|
|
70
74
|
if isinstance(obj, (list, tuple)):
|
|
@@ -433,7 +433,7 @@ class Table(Layout):
|
|
|
433
433
|
filter(
|
|
434
434
|
lambda c: column_number in (c.column_number, c.column_number + c.column_span - 1), # type: ignore
|
|
435
435
|
all_cells,
|
|
436
|
-
)
|
|
436
|
+
)
|
|
437
437
|
)
|
|
438
438
|
column_cells.sort(key=lambda c: c.row_number) # type: ignore
|
|
439
439
|
return column_cells # type: ignore
|
|
@@ -24,7 +24,7 @@ import catalogue # type: ignore
|
|
|
24
24
|
from tabulate import tabulate
|
|
25
25
|
from termcolor import colored
|
|
26
26
|
|
|
27
|
-
from .base import DatasetBase
|
|
27
|
+
from .base import CustomDataset, DatasetBase
|
|
28
28
|
|
|
29
29
|
__all__ = ["dataset_registry", "get_dataset", "print_dataset_infos"]
|
|
30
30
|
|
|
@@ -68,7 +68,10 @@ def print_dataset_infos(add_license: bool = True, add_info: bool = True) -> None
|
|
|
68
68
|
|
|
69
69
|
for dataset in data.items():
|
|
70
70
|
info = [dataset[0]]
|
|
71
|
-
|
|
71
|
+
if isinstance(dataset[1], CustomDataset):
|
|
72
|
+
ds = dataset[1]
|
|
73
|
+
else:
|
|
74
|
+
ds = dataset[1]()
|
|
72
75
|
info.append(ds.dataset_info.type)
|
|
73
76
|
if add_license:
|
|
74
77
|
info.append(ds.dataset_info.license) # pylint: disable=W0212
|
|
@@ -123,7 +123,7 @@ class DetectResultGenerator:
|
|
|
123
123
|
"""
|
|
124
124
|
sane_detect_results = []
|
|
125
125
|
for detect_result in detect_result_list:
|
|
126
|
-
if detect_result.box:
|
|
126
|
+
if detect_result.box is not None:
|
|
127
127
|
ulx, uly, lrx, lry = detect_result.box
|
|
128
128
|
if ulx >= 0 and lrx - ulx >= 0 and uly >= 0 and lry - uly >= 0:
|
|
129
129
|
sane_detect_results.append(detect_result)
|
|
@@ -37,6 +37,8 @@ from ..extern.hfdetr import HFDetrDerivedDetector
|
|
|
37
37
|
from ..mapper.hfstruct import DetrDataCollator, image_to_hf_detr_training
|
|
38
38
|
from ..pipe.base import PipelineComponent
|
|
39
39
|
from ..pipe.registry import pipeline_component_registry
|
|
40
|
+
from ..utils.error import DependencyError
|
|
41
|
+
from ..utils.file_utils import wandb_available
|
|
40
42
|
from ..utils.logger import LoggingRecord, logger
|
|
41
43
|
from ..utils.types import PathLikeOrStr
|
|
42
44
|
from ..utils.utils import string_to_dict
|
|
@@ -56,6 +58,9 @@ with try_import() as hf_import_guard:
|
|
|
56
58
|
TrainingArguments,
|
|
57
59
|
)
|
|
58
60
|
|
|
61
|
+
with try_import() as wb_import_guard:
|
|
62
|
+
import wandb
|
|
63
|
+
|
|
59
64
|
|
|
60
65
|
class DetrDerivedTrainer(Trainer):
|
|
61
66
|
"""
|
|
@@ -74,16 +79,18 @@ class DetrDerivedTrainer(Trainer):
|
|
|
74
79
|
args: TrainingArguments,
|
|
75
80
|
data_collator: DetrDataCollator,
|
|
76
81
|
train_dataset: DatasetAdapter,
|
|
82
|
+
eval_dataset: Optional[DatasetBase] = None,
|
|
77
83
|
):
|
|
78
84
|
self.evaluator: Optional[Evaluator] = None
|
|
79
85
|
self.build_eval_kwargs: Optional[dict[str, Any]] = None
|
|
80
|
-
super().__init__(model, args, data_collator, train_dataset)
|
|
86
|
+
super().__init__(model, args, data_collator, train_dataset, eval_dataset=eval_dataset)
|
|
81
87
|
|
|
82
88
|
def setup_evaluator(
|
|
83
89
|
self,
|
|
84
90
|
dataset_val: DatasetBase,
|
|
85
91
|
pipeline_component: PipelineComponent,
|
|
86
92
|
metric: Union[Type[MetricBase], MetricBase],
|
|
93
|
+
run: Optional[wandb.sdk.wandb_run.Run] = None,
|
|
87
94
|
**build_eval_kwargs: Union[str, int],
|
|
88
95
|
) -> None:
|
|
89
96
|
"""
|
|
@@ -93,10 +100,11 @@ class DetrDerivedTrainer(Trainer):
|
|
|
93
100
|
:param dataset_val: dataset on which to run evaluation
|
|
94
101
|
:param pipeline_component: pipeline component to plug into the evaluator
|
|
95
102
|
:param metric: A metric class
|
|
103
|
+
:param run: WandB run
|
|
96
104
|
:param build_eval_kwargs:
|
|
97
105
|
"""
|
|
98
106
|
|
|
99
|
-
self.evaluator = Evaluator(dataset_val, pipeline_component, metric, num_threads=1)
|
|
107
|
+
self.evaluator = Evaluator(dataset_val, pipeline_component, metric, num_threads=1, run=run)
|
|
100
108
|
assert self.evaluator.pipe_component
|
|
101
109
|
for comp in self.evaluator.pipe_component.pipe_components:
|
|
102
110
|
comp.clear_predictor()
|
|
@@ -205,12 +213,19 @@ def train_hf_detr(
|
|
|
205
213
|
"remove_unused_columns": False,
|
|
206
214
|
"per_device_train_batch_size": 2,
|
|
207
215
|
"max_steps": number_samples,
|
|
208
|
-
"
|
|
216
|
+
"eval_strategy": (
|
|
209
217
|
"steps"
|
|
210
|
-
if (
|
|
218
|
+
if (
|
|
219
|
+
dataset_val is not None
|
|
220
|
+
and (metric is not None or metric_name is not None)
|
|
221
|
+
and pipeline_component_name is not None
|
|
222
|
+
)
|
|
211
223
|
else "no"
|
|
212
224
|
),
|
|
213
225
|
"eval_steps": 5000,
|
|
226
|
+
"use_wandb": False,
|
|
227
|
+
"wandb_project": None,
|
|
228
|
+
"wandb_repo": "deepdoctection",
|
|
214
229
|
}
|
|
215
230
|
|
|
216
231
|
for conf in config_overwrite:
|
|
@@ -224,6 +239,23 @@ def train_hf_detr(
|
|
|
224
239
|
pass
|
|
225
240
|
conf_dict[key] = val
|
|
226
241
|
|
|
242
|
+
use_wandb = conf_dict.pop("use_wandb")
|
|
243
|
+
wandb_project = str(conf_dict.pop("wandb_project"))
|
|
244
|
+
wandb_repo = str(conf_dict.pop("wandb_repo"))
|
|
245
|
+
|
|
246
|
+
# Initialize Wandb, if necessary
|
|
247
|
+
run = None
|
|
248
|
+
if use_wandb:
|
|
249
|
+
if not wandb_available():
|
|
250
|
+
raise DependencyError("WandB must be installed separately")
|
|
251
|
+
run = wandb.init(project=wandb_project, config=conf_dict)
|
|
252
|
+
run._label(repo=wandb_repo) # pylint: disable=W0212
|
|
253
|
+
os.environ["WANDB_DISABLED"] = "False"
|
|
254
|
+
os.environ["WANDB_WATCH"] = "True"
|
|
255
|
+
os.environ["WANDB_PROJECT"] = wandb_project
|
|
256
|
+
else:
|
|
257
|
+
os.environ["WANDB_DISABLED"] = "True"
|
|
258
|
+
|
|
227
259
|
# Will inform about dataloader warnings if max_steps exceeds length of dataset
|
|
228
260
|
if conf_dict["max_steps"] > number_samples: # type: ignore
|
|
229
261
|
logger.warning(
|
|
@@ -232,7 +264,7 @@ def train_hf_detr(
|
|
|
232
264
|
)
|
|
233
265
|
)
|
|
234
266
|
|
|
235
|
-
arguments = TrainingArguments(**conf_dict)
|
|
267
|
+
arguments = TrainingArguments(**conf_dict) # pylint: disable=E1123
|
|
236
268
|
logger.info(LoggingRecord(f"Config: \n {arguments.to_dict()}", arguments.to_dict()))
|
|
237
269
|
|
|
238
270
|
id2label = {int(k) - 1: v for v, k in categories_dict_name_as_key.items()}
|
|
@@ -252,9 +284,9 @@ def train_hf_detr(
|
|
|
252
284
|
pretrained_model_name_or_path=path_feature_extractor_config_json
|
|
253
285
|
)
|
|
254
286
|
data_collator = DetrDataCollator(feature_extractor)
|
|
255
|
-
trainer = DetrDerivedTrainer(model, arguments, data_collator, dataset)
|
|
287
|
+
trainer = DetrDerivedTrainer(model, arguments, data_collator, dataset, eval_dataset=dataset_val)
|
|
256
288
|
|
|
257
|
-
if arguments.
|
|
289
|
+
if arguments.eval_strategy in (IntervalStrategy.STEPS,):
|
|
258
290
|
categories = dataset_val.dataflow.categories.get_categories(filtered=True) # type: ignore
|
|
259
291
|
detector = HFDetrDerivedDetector(
|
|
260
292
|
path_config_json, path_weights, path_feature_extractor_config_json, categories # type: ignore
|
|
@@ -266,6 +298,6 @@ def train_hf_detr(
|
|
|
266
298
|
metric = metric_registry.get(metric_name)
|
|
267
299
|
assert metric is not None
|
|
268
300
|
|
|
269
|
-
trainer.setup_evaluator(dataset_val, pipeline_component, metric) # type: ignore
|
|
301
|
+
trainer.setup_evaluator(dataset_val, pipeline_component, metric, run, **build_val_dict) # type: ignore
|
|
270
302
|
|
|
271
303
|
trainer.train()
|
|
@@ -395,7 +395,7 @@ def train_hf_layoutlm(
|
|
|
395
395
|
"remove_unused_columns": False,
|
|
396
396
|
"per_device_train_batch_size": 8,
|
|
397
397
|
"max_steps": number_samples,
|
|
398
|
-
"
|
|
398
|
+
"eval_strategy": (
|
|
399
399
|
"steps"
|
|
400
400
|
if (dataset_val is not None and metric is not None and pipeline_component_name is not None)
|
|
401
401
|
else "no"
|
|
@@ -475,7 +475,7 @@ def train_hf_layoutlm(
|
|
|
475
475
|
)
|
|
476
476
|
trainer = LayoutLMTrainer(model, arguments, data_collator, dataset, eval_dataset=dataset_val)
|
|
477
477
|
|
|
478
|
-
if arguments.
|
|
478
|
+
if arguments.eval_strategy in (IntervalStrategy.STEPS,):
|
|
479
479
|
assert metric is not None # silence mypy
|
|
480
480
|
if dataset_type == DatasetType.SEQUENCE_CLASSIFICATION:
|
|
481
481
|
categories = dataset_val.dataflow.categories.get_categories(filtered=True) # type: ignore
|