From 6973990b7492bb51ba11110ac64de0743d43bd3e Mon Sep 17 00:00:00 2001 From: Ccc <52520497+juncaipeng@users.noreply.github.com> Date: Thu, 5 Jan 2023 17:34:23 +0800 Subject: [PATCH] [Feature] Refactor optimizer as component (#2893) --- configs/_base_/ade20k.yml | 2 +- configs/_base_/autonue.yml | 2 +- configs/_base_/chase_db1.yml | 2 +- configs/_base_/cityscapes.yml | 2 +- configs/_base_/coco_stuff.yml | 2 +- configs/_base_/drive.yml | 2 +- configs/_base_/hrf.yml | 2 +- configs/_base_/pascal_context.yml | 2 +- configs/_base_/pascal_voc12.yml | 2 +- configs/_base_/stare.yml | 2 +- .../bisenet_cityscapes_1024x1024_160k.yml | 2 +- ..._resnet18_os8_cityscapes_1024x512_160k.yml | 2 +- ..._resnet101_os8_cityscapes_1024x512_80k.yml | 2 +- ...t_resnet50_os8_cityscapes_1024x512_80k.yml | 2 +- .../ddrnet23_cityscapes_1024x1024_120k.yml | 2 +- ..._resnet101_os8_cityscapes_1024x512_80k.yml | 2 +- ..._resnet101_os8_cityscapes_1024x512_80k.yml | 2 +- ...net_resnet101_os8_voc12aug_512x512_40k.yml | 2 +- ...t_resnet50_os8_cityscapes_1024x512_80k.yml | 2 +- ...lnet_resnet50_os8_voc12aug_512x512_40k.yml | 2 +- ..._resnet101_os8_cityscapes_1024x512_80k.yml | 2 +- ...net_resnet101_os8_voc12aug_512x512_40k.yml | 2 +- ...t_resnet50_os8_cityscapes_1024x512_80k.yml | 2 +- ...anet_resnet50_os8_voc12aug_512x512_40k.yml | 2 +- ..._resnet101_os8_cityscapes_1024x512_80k.yml | 2 +- configs/enet/enet_cityscapes_1024x512_80k.yml | 2 +- .../espnet_cityscapes_1024x512_120k.yml | 2 +- .../espnetv1_cityscapes_1024x512_120k.yml | 2 +- configs/fcn/fcn_hrnetw18_pphumanseg14k.yml | 2 +- .../hardnet_cityscapes_1024x1024_160k.yml | 2 +- ...t_W48_contrast_cityscapes_1024x512_60k.yml | 4 +- ...t_resnet101_os8_cityscapes_769x769_80k.yml | 2 +- ...net_resnet101_os8_voc12aug_512x512_40k.yml | 2 +- ...et_resnet50_os8_cityscapes_769x769_80k.yml | 2 +- ...anet_resnet50_os8_voc12aug_512x512_40k.yml | 2 +- .../lpsnet_m_cityscapes_1536x1024_200k.yml | 2 +- ..._hrnetv2_psa_cityscapes_1024x2048_150k.yml | 8 +- ...rnet_hrnetw18_cityscapes_1024x512_160k.yml | 2 +- ...ityscapes_1024x512_160k_lovasz_softmax.yml | 2 +- ...t_hrnetw18_road_extraction_768x768_15k.yml | 2 +- ...ad_extraction_768x768_15k_lovasz_hinge.yml | 2 +- .../ocrnet_hrnetw18_voc12aug_512x512_40k.yml | 2 +- ...rnet_hrnetw48_cityscapes_1024x512_160k.yml | 2 +- ...crnet_hrnetw48_cityscapes_1024x512_40k.yml | 2 +- ...t_hrnetw48_cityscapes_1024x512_40k_SCL.yml | 2 +- ..._resnet101_os8_cityscapes_512x1024_40k.yml | 2 +- ...d_resnet50_os8_cityscapes_1024x512_80k.yml | 2 +- ...rend_resnet50_os8_voc12aug_512x512_40k.yml | 2 +- .../portraitnet_eg1800_224x224_46k.yml | 2 +- .../pp_humanseg_lite_export_398x224.yml | 6 - .../pp_humanseg_lite_mini_supervisely.yml | 8 +- .../pp_liteseg_stdc1_camvid_960x720_10k.yml | 2 +- configs/pssl/pp_liteseg_stdc1_pssl.yml | 2 +- configs/pssl/stdc1_seg_pssl.yml | 2 +- .../bisenet_optic_disc_512x512_1k.yml | 2 +- ...et18_os8_optic_disc_512x512_1k_student.yml | 2 +- ...et50_os8_optic_disc_512x512_1k_teacher.yml | 2 +- .../pp_liteseg_optic_disc_512x512_1k.yml | 2 +- .../rtformer_base_ade20k_512x512_160k.yml | 10 - ...rtformer_base_cityscapes_1024x512_120k.yml | 9 - .../rtformer_slim_ade20k_512x512_160k.yml | 10 - ...rtformer_slim_cityscapes_1024x512_120k.yml | 9 - ..._resnet18_os8_cityscapes_1024x1024_80k.yml | 2 +- configs/smrt/base_cfg.yml | 2 +- .../topformer_base_ade20k_512x512_160k.yml | 10 - .../topformer_small_ade20k_512x512_160k.yml | 10 - .../topformer_tiny_ade20k_512x512_160k.yml | 10 - ..._resnet101_os8_cityscapes_512x1024_40k.yml | 2 +- paddleseg/__init__.py | 2 +- paddleseg/cvlibs/callbacks.py | 279 ------------------ paddleseg/cvlibs/config.py | 131 +++----- paddleseg/cvlibs/config_checker.py | 142 +++++---- paddleseg/cvlibs/manager.py | 1 + paddleseg/datasets/ade.py | 4 +- paddleseg/datasets/chase_db1.py | 4 +- paddleseg/datasets/cityscapes.py | 4 +- paddleseg/datasets/cocostuff.py | 4 +- paddleseg/datasets/drive.py | 4 +- paddleseg/datasets/eg1800.py | 4 +- paddleseg/datasets/hrf.py | 4 +- .../mini_deep_globe_road_extraction.py | 4 +- paddleseg/datasets/optic_disc_seg.py | 4 +- paddleseg/datasets/pascal_context.py | 4 +- paddleseg/datasets/pp_humanseg14k.py | 4 +- paddleseg/datasets/pssl.py | 4 +- paddleseg/datasets/stare.py | 4 +- paddleseg/datasets/supervisely.py | 4 +- paddleseg/datasets/voc.py | 4 +- paddleseg/models/hrnet_contrast.py | 12 +- paddleseg/optimizers/__init__.py | 14 + paddleseg/optimizers/optimizer.py | 234 +++++++++++++++ tools/export.py | 2 - 92 files changed, 478 insertions(+), 607 deletions(-) delete mode 100644 paddleseg/cvlibs/callbacks.py create mode 100644 paddleseg/optimizers/__init__.py create mode 100644 paddleseg/optimizers/optimizer.py diff --git a/configs/_base_/ade20k.yml b/configs/_base_/ade20k.yml index 595f02243e..44683030d5 100644 --- a/configs/_base_/ade20k.yml +++ b/configs/_base_/ade20k.yml @@ -28,7 +28,7 @@ val_dataset: optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/_base_/autonue.yml b/configs/_base_/autonue.yml index b957f7d5b0..6cfec46e1e 100644 --- a/configs/_base_/autonue.yml +++ b/configs/_base_/autonue.yml @@ -39,7 +39,7 @@ val_dataset: optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0001 diff --git a/configs/_base_/chase_db1.yml b/configs/_base_/chase_db1.yml index 2fd848f5f9..c32898d09c 100644 --- a/configs/_base_/chase_db1.yml +++ b/configs/_base_/chase_db1.yml @@ -29,7 +29,7 @@ val_dataset: optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/_base_/cityscapes.yml b/configs/_base_/cityscapes.yml index 4afbcbe944..f71e8f8845 100644 --- a/configs/_base_/cityscapes.yml +++ b/configs/_base_/cityscapes.yml @@ -28,7 +28,7 @@ val_dataset: optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/_base_/coco_stuff.yml b/configs/_base_/coco_stuff.yml index 77d9e321f4..026b523a29 100644 --- a/configs/_base_/coco_stuff.yml +++ b/configs/_base_/coco_stuff.yml @@ -28,7 +28,7 @@ val_dataset: optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/_base_/drive.yml b/configs/_base_/drive.yml index 4df980eacc..2b2092f1ea 100644 --- a/configs/_base_/drive.yml +++ b/configs/_base_/drive.yml @@ -29,7 +29,7 @@ val_dataset: optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/_base_/hrf.yml b/configs/_base_/hrf.yml index ff4ad7b1ba..045e859c92 100644 --- a/configs/_base_/hrf.yml +++ b/configs/_base_/hrf.yml @@ -31,7 +31,7 @@ val_dataset: optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/_base_/pascal_context.yml b/configs/_base_/pascal_context.yml index f566122cbc..e6a3168a17 100644 --- a/configs/_base_/pascal_context.yml +++ b/configs/_base_/pascal_context.yml @@ -30,7 +30,7 @@ val_dataset: optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/_base_/pascal_voc12.yml b/configs/_base_/pascal_voc12.yml index 510aa14eb3..2769fd1631 100644 --- a/configs/_base_/pascal_voc12.yml +++ b/configs/_base_/pascal_voc12.yml @@ -30,7 +30,7 @@ val_dataset: optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/_base_/stare.yml b/configs/_base_/stare.yml index 4c5735a546..b911127f58 100644 --- a/configs/_base_/stare.yml +++ b/configs/_base_/stare.yml @@ -28,7 +28,7 @@ val_dataset: mode: val optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/bisenet/bisenet_cityscapes_1024x1024_160k.yml b/configs/bisenet/bisenet_cityscapes_1024x1024_160k.yml index d239154042..3963cbb961 100644 --- a/configs/bisenet/bisenet_cityscapes_1024x1024_160k.yml +++ b/configs/bisenet/bisenet_cityscapes_1024x1024_160k.yml @@ -5,7 +5,7 @@ model: num_classes: 19 optimizer: - type: sgd + type: SGD weight_decay: 0.0005 loss: diff --git a/configs/bisenetv1/bisenetv1_resnet18_os8_cityscapes_1024x512_160k.yml b/configs/bisenetv1/bisenetv1_resnet18_os8_cityscapes_1024x512_160k.yml index 41d4dd7a2d..cf9703ec57 100644 --- a/configs/bisenetv1/bisenetv1_resnet18_os8_cityscapes_1024x512_160k.yml +++ b/configs/bisenetv1/bisenetv1_resnet18_os8_cityscapes_1024x512_160k.yml @@ -11,7 +11,7 @@ model: pretrained: https://bj.bcebos.com/paddleseg/dygraph/resnet18_vd_ssld_v2.tar.gz optimizer: - type: sgd + type: SGD weight_decay: 0.0005 loss: diff --git a/configs/danet/danet_resnet101_os8_cityscapes_1024x512_80k.yml b/configs/danet/danet_resnet101_os8_cityscapes_1024x512_80k.yml index dce1e0a7a5..35ee7bc68d 100644 --- a/configs/danet/danet_resnet101_os8_cityscapes_1024x512_80k.yml +++ b/configs/danet/danet_resnet101_os8_cityscapes_1024x512_80k.yml @@ -13,7 +13,7 @@ model: backbone_indices: [2, 3] optimizer: - type: sgd + type: SGD lr_scheduler: type: PolynomialDecay diff --git a/configs/danet/danet_resnet50_os8_cityscapes_1024x512_80k.yml b/configs/danet/danet_resnet50_os8_cityscapes_1024x512_80k.yml index 06b95c0b7e..bae67ca235 100644 --- a/configs/danet/danet_resnet50_os8_cityscapes_1024x512_80k.yml +++ b/configs/danet/danet_resnet50_os8_cityscapes_1024x512_80k.yml @@ -13,7 +13,7 @@ model: backbone_indices: [2, 3] optimizer: - type: sgd + type: SGD lr_scheduler: type: PolynomialDecay diff --git a/configs/ddrnet/ddrnet23_cityscapes_1024x1024_120k.yml b/configs/ddrnet/ddrnet23_cityscapes_1024x1024_120k.yml index 5a7832fb8b..7ad4cbcf56 100644 --- a/configs/ddrnet/ddrnet23_cityscapes_1024x1024_120k.yml +++ b/configs/ddrnet/ddrnet23_cityscapes_1024x1024_120k.yml @@ -9,7 +9,7 @@ model: pretrained: https://bj.bcebos.com/paddleseg/dygraph/cityscapes/ddrnet23_cityscapes_1024x1024_120k/pretrain/model.pdparams optimizer: - type: sgd + type: SGD weight_decay: 0.0005 loss: diff --git a/configs/dmnet/dmnet_resnet101_os8_cityscapes_1024x512_80k.yml b/configs/dmnet/dmnet_resnet101_os8_cityscapes_1024x512_80k.yml index 00a9733865..3342292269 100644 --- a/configs/dmnet/dmnet_resnet101_os8_cityscapes_1024x512_80k.yml +++ b/configs/dmnet/dmnet_resnet101_os8_cityscapes_1024x512_80k.yml @@ -11,7 +11,7 @@ model: pretrained: https://bj.bcebos.com/paddleseg/dygraph/resnet101_vd_ssld.tar.gz optimizer: - type: sgd + type: SGD weight_decay: 0.0005 loss: diff --git a/configs/dnlnet/dnlnet_resnet101_os8_cityscapes_1024x512_80k.yml b/configs/dnlnet/dnlnet_resnet101_os8_cityscapes_1024x512_80k.yml index 71101d9175..b157d44c54 100644 --- a/configs/dnlnet/dnlnet_resnet101_os8_cityscapes_1024x512_80k.yml +++ b/configs/dnlnet/dnlnet_resnet101_os8_cityscapes_1024x512_80k.yml @@ -12,7 +12,7 @@ model: num_classes: 19 optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.00004 diff --git a/configs/dnlnet/dnlnet_resnet101_os8_voc12aug_512x512_40k.yml b/configs/dnlnet/dnlnet_resnet101_os8_voc12aug_512x512_40k.yml index 23bc2cc699..717d232186 100644 --- a/configs/dnlnet/dnlnet_resnet101_os8_voc12aug_512x512_40k.yml +++ b/configs/dnlnet/dnlnet_resnet101_os8_voc12aug_512x512_40k.yml @@ -8,7 +8,7 @@ model: pretrained: https://bj.bcebos.com/paddleseg/dygraph/resnet101_vd_ssld.tar.gz optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-05 diff --git a/configs/dnlnet/dnlnet_resnet50_os8_cityscapes_1024x512_80k.yml b/configs/dnlnet/dnlnet_resnet50_os8_cityscapes_1024x512_80k.yml index 2f49459bb1..c76ec58c1b 100644 --- a/configs/dnlnet/dnlnet_resnet50_os8_cityscapes_1024x512_80k.yml +++ b/configs/dnlnet/dnlnet_resnet50_os8_cityscapes_1024x512_80k.yml @@ -12,7 +12,7 @@ model: num_classes: 19 optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.00004 diff --git a/configs/dnlnet/dnlnet_resnet50_os8_voc12aug_512x512_40k.yml b/configs/dnlnet/dnlnet_resnet50_os8_voc12aug_512x512_40k.yml index d6417c6f7a..41638de212 100644 --- a/configs/dnlnet/dnlnet_resnet50_os8_voc12aug_512x512_40k.yml +++ b/configs/dnlnet/dnlnet_resnet50_os8_voc12aug_512x512_40k.yml @@ -8,7 +8,7 @@ model: pretrained: https://bj.bcebos.com/paddleseg/dygraph/resnet50_vd_ssld_v2.tar.gz optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-05 diff --git a/configs/emanet/emanet_resnet101_os8_cityscapes_1024x512_80k.yml b/configs/emanet/emanet_resnet101_os8_cityscapes_1024x512_80k.yml index 45c9641eed..b5b763d5a5 100644 --- a/configs/emanet/emanet_resnet101_os8_cityscapes_1024x512_80k.yml +++ b/configs/emanet/emanet_resnet101_os8_cityscapes_1024x512_80k.yml @@ -20,7 +20,7 @@ model: align_corners: False optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0005 diff --git a/configs/emanet/emanet_resnet101_os8_voc12aug_512x512_40k.yml b/configs/emanet/emanet_resnet101_os8_voc12aug_512x512_40k.yml index df7b72b920..3674c6c05f 100644 --- a/configs/emanet/emanet_resnet101_os8_voc12aug_512x512_40k.yml +++ b/configs/emanet/emanet_resnet101_os8_voc12aug_512x512_40k.yml @@ -16,7 +16,7 @@ model: align_corners: True optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0005 diff --git a/configs/emanet/emanet_resnet50_os8_cityscapes_1024x512_80k.yml b/configs/emanet/emanet_resnet50_os8_cityscapes_1024x512_80k.yml index 4e8c1309e5..cd7c13383c 100644 --- a/configs/emanet/emanet_resnet50_os8_cityscapes_1024x512_80k.yml +++ b/configs/emanet/emanet_resnet50_os8_cityscapes_1024x512_80k.yml @@ -20,7 +20,7 @@ model: align_corners: False optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0005 diff --git a/configs/emanet/emanet_resnet50_os8_voc12aug_512x512_40k.yml b/configs/emanet/emanet_resnet50_os8_voc12aug_512x512_40k.yml index e177de7657..8dd14b48e7 100644 --- a/configs/emanet/emanet_resnet50_os8_voc12aug_512x512_40k.yml +++ b/configs/emanet/emanet_resnet50_os8_voc12aug_512x512_40k.yml @@ -17,7 +17,7 @@ model: align_corners: True optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0005 diff --git a/configs/encnet/encnet_resnet101_os8_cityscapes_1024x512_80k.yml b/configs/encnet/encnet_resnet101_os8_cityscapes_1024x512_80k.yml index 886a4720a9..7c59862e6d 100644 --- a/configs/encnet/encnet_resnet101_os8_cityscapes_1024x512_80k.yml +++ b/configs/encnet/encnet_resnet101_os8_cityscapes_1024x512_80k.yml @@ -16,7 +16,7 @@ model: add_lateral: True optimizer: - type: sgd + type: SGD weight_decay: 0.0005 loss: diff --git a/configs/enet/enet_cityscapes_1024x512_80k.yml b/configs/enet/enet_cityscapes_1024x512_80k.yml index 7abfa2f89b..5adbfb53d1 100644 --- a/configs/enet/enet_cityscapes_1024x512_80k.yml +++ b/configs/enet/enet_cityscapes_1024x512_80k.yml @@ -21,7 +21,7 @@ model: optimizer: _inherited_: False - type: adam + type: Adam weight_decay: 0.0002 lr_scheduler: diff --git a/configs/espnet/espnet_cityscapes_1024x512_120k.yml b/configs/espnet/espnet_cityscapes_1024x512_120k.yml index 91879db8fb..5b874f101e 100644 --- a/configs/espnet/espnet_cityscapes_1024x512_120k.yml +++ b/configs/espnet/espnet_cityscapes_1024x512_120k.yml @@ -6,7 +6,7 @@ iters: 120000 optimizer: _inherited_: False - type: adam + type: Adam weight_decay: 0.0002 lr_scheduler: diff --git a/configs/espnetv1/espnetv1_cityscapes_1024x512_120k.yml b/configs/espnetv1/espnetv1_cityscapes_1024x512_120k.yml index 4cf93318e4..f14bd613f1 100644 --- a/configs/espnetv1/espnetv1_cityscapes_1024x512_120k.yml +++ b/configs/espnetv1/espnetv1_cityscapes_1024x512_120k.yml @@ -5,7 +5,7 @@ iters: 120000 optimizer: _inherited_: False - type: adam + type: Adam weight_decay: 0.0002 lr_scheduler: diff --git a/configs/fcn/fcn_hrnetw18_pphumanseg14k.yml b/configs/fcn/fcn_hrnetw18_pphumanseg14k.yml index d7064f2154..ab82c1b92f 100644 --- a/configs/fcn/fcn_hrnetw18_pphumanseg14k.yml +++ b/configs/fcn/fcn_hrnetw18_pphumanseg14k.yml @@ -34,7 +34,7 @@ model: backbone_indices: [-1] optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0005 diff --git a/configs/hardnet/hardnet_cityscapes_1024x1024_160k.yml b/configs/hardnet/hardnet_cityscapes_1024x1024_160k.yml index 74a5bd82de..2537931c65 100644 --- a/configs/hardnet/hardnet_cityscapes_1024x1024_160k.yml +++ b/configs/hardnet/hardnet_cityscapes_1024x1024_160k.yml @@ -8,7 +8,7 @@ lr_scheduler: learning_rate: 0.02 optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 5.0e-4 diff --git a/configs/hrnet_w48_contrast/HRNet_W48_contrast_cityscapes_1024x512_60k.yml b/configs/hrnet_w48_contrast/HRNet_W48_contrast_cityscapes_1024x512_60k.yml index 1659b5035d..5c0c036f95 100644 --- a/configs/hrnet_w48_contrast/HRNet_W48_contrast_cityscapes_1024x512_60k.yml +++ b/configs/hrnet_w48_contrast/HRNet_W48_contrast_cityscapes_1024x512_60k.yml @@ -5,7 +5,7 @@ iters: 60000 optimizer: - type: sgd + type: SGD weight_decay: 0.0002 loss: @@ -24,6 +24,6 @@ model: backbone: type: HRNet_W48 pretrained: https://bj.bcebos.com/paddleseg/dygraph/hrnet_w48_ssld.tar.gz - in_channels: 720 + bb_channels: 720 drop_prob: 0.1 proj_dim: 720 diff --git a/configs/isanet/isanet_resnet101_os8_cityscapes_769x769_80k.yml b/configs/isanet/isanet_resnet101_os8_cityscapes_769x769_80k.yml index 86a595e1bb..6ada3164d0 100644 --- a/configs/isanet/isanet_resnet101_os8_cityscapes_769x769_80k.yml +++ b/configs/isanet/isanet_resnet101_os8_cityscapes_769x769_80k.yml @@ -13,7 +13,7 @@ model: num_classes: 19 optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.00001 diff --git a/configs/isanet/isanet_resnet101_os8_voc12aug_512x512_40k.yml b/configs/isanet/isanet_resnet101_os8_voc12aug_512x512_40k.yml index e6336d688f..054a31f435 100644 --- a/configs/isanet/isanet_resnet101_os8_voc12aug_512x512_40k.yml +++ b/configs/isanet/isanet_resnet101_os8_voc12aug_512x512_40k.yml @@ -10,7 +10,7 @@ model: align_corners: True optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-05 diff --git a/configs/isanet/isanet_resnet50_os8_cityscapes_769x769_80k.yml b/configs/isanet/isanet_resnet50_os8_cityscapes_769x769_80k.yml index 4ffb8b54ed..8cec5a8179 100644 --- a/configs/isanet/isanet_resnet50_os8_cityscapes_769x769_80k.yml +++ b/configs/isanet/isanet_resnet50_os8_cityscapes_769x769_80k.yml @@ -13,7 +13,7 @@ model: num_classes: 19 optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.00001 diff --git a/configs/isanet/isanet_resnet50_os8_voc12aug_512x512_40k.yml b/configs/isanet/isanet_resnet50_os8_voc12aug_512x512_40k.yml index 5a875317e5..37e9b426f8 100644 --- a/configs/isanet/isanet_resnet50_os8_voc12aug_512x512_40k.yml +++ b/configs/isanet/isanet_resnet50_os8_voc12aug_512x512_40k.yml @@ -10,7 +10,7 @@ model: align_corners: True optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.00001 diff --git a/configs/lpsnet/lpsnet_m_cityscapes_1536x1024_200k.yml b/configs/lpsnet/lpsnet_m_cityscapes_1536x1024_200k.yml index 7a8cd12e04..e71907645f 100644 --- a/configs/lpsnet/lpsnet_m_cityscapes_1536x1024_200k.yml +++ b/configs/lpsnet/lpsnet_m_cityscapes_1536x1024_200k.yml @@ -27,7 +27,7 @@ val_dataset: std: [0.229, 0.224, 0.225] optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0005 diff --git a/configs/mscale_ocrnet/mscale_ocrnet_hrnetv2_psa_cityscapes_1024x2048_150k.yml b/configs/mscale_ocrnet/mscale_ocrnet_hrnetv2_psa_cityscapes_1024x2048_150k.yml index 991aa5c6d2..0e6ed761e4 100644 --- a/configs/mscale_ocrnet/mscale_ocrnet_hrnetv2_psa_cityscapes_1024x2048_150k.yml +++ b/configs/mscale_ocrnet/mscale_ocrnet_hrnetv2_psa_cityscapes_1024x2048_150k.yml @@ -34,12 +34,6 @@ val_dataset: std: [0.229, 0.224, 0.225] mode: val -export: - transforms: - - type: Normalize - mean: [0.485, 0.456, 0.406] - std: [0.229, 0.224, 0.225] - model: type: MscaleOCRNet num_classes: 19 @@ -50,7 +44,7 @@ model: pretrained: https://paddleseg.bj.bcebos.com/dygraph/cityscapes/mscale_ocrnet_hrnetv2_psa_cityscapes_1024x2048_150k/mscale_ocrnet_pretrained_mappilary.zip optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 5.0e-4 diff --git a/configs/ocrnet/ocrnet_hrnetw18_cityscapes_1024x512_160k.yml b/configs/ocrnet/ocrnet_hrnetw18_cityscapes_1024x512_160k.yml index 6c2481be4f..350311f35c 100644 --- a/configs/ocrnet/ocrnet_hrnetw18_cityscapes_1024x512_160k.yml +++ b/configs/ocrnet/ocrnet_hrnetw18_cityscapes_1024x512_160k.yml @@ -12,7 +12,7 @@ model: backbone_indices: [0] optimizer: - type: sgd + type: SGD lr_scheduler: type: PolynomialDecay diff --git a/configs/ocrnet/ocrnet_hrnetw18_cityscapes_1024x512_160k_lovasz_softmax.yml b/configs/ocrnet/ocrnet_hrnetw18_cityscapes_1024x512_160k_lovasz_softmax.yml index 24e2cd5896..5e56788743 100644 --- a/configs/ocrnet/ocrnet_hrnetw18_cityscapes_1024x512_160k_lovasz_softmax.yml +++ b/configs/ocrnet/ocrnet_hrnetw18_cityscapes_1024x512_160k_lovasz_softmax.yml @@ -11,7 +11,7 @@ model: backbone_indices: [0] optimizer: - type: sgd + type: SGD lr_scheduler: type: PolynomialDecay diff --git a/configs/ocrnet/ocrnet_hrnetw18_road_extraction_768x768_15k.yml b/configs/ocrnet/ocrnet_hrnetw18_road_extraction_768x768_15k.yml index b04f449803..bb4b2acb02 100644 --- a/configs/ocrnet/ocrnet_hrnetw18_road_extraction_768x768_15k.yml +++ b/configs/ocrnet/ocrnet_hrnetw18_road_extraction_768x768_15k.yml @@ -32,7 +32,7 @@ model: backbone_indices: [0] optimizer: - type: sgd + type: SGD lr_scheduler: type: PolynomialDecay diff --git a/configs/ocrnet/ocrnet_hrnetw18_road_extraction_768x768_15k_lovasz_hinge.yml b/configs/ocrnet/ocrnet_hrnetw18_road_extraction_768x768_15k_lovasz_hinge.yml index 5081e27139..a3863beff2 100644 --- a/configs/ocrnet/ocrnet_hrnetw18_road_extraction_768x768_15k_lovasz_hinge.yml +++ b/configs/ocrnet/ocrnet_hrnetw18_road_extraction_768x768_15k_lovasz_hinge.yml @@ -32,7 +32,7 @@ model: backbone_indices: [0] optimizer: - type: sgd + type: SGD lr_scheduler: type: PolynomialDecay diff --git a/configs/ocrnet/ocrnet_hrnetw18_voc12aug_512x512_40k.yml b/configs/ocrnet/ocrnet_hrnetw18_voc12aug_512x512_40k.yml index 6a21452897..6225cfea72 100644 --- a/configs/ocrnet/ocrnet_hrnetw18_voc12aug_512x512_40k.yml +++ b/configs/ocrnet/ocrnet_hrnetw18_voc12aug_512x512_40k.yml @@ -8,7 +8,7 @@ model: backbone_indices: [0] optimizer: - type: sgd + type: SGD lr_scheduler: type: PolynomialDecay diff --git a/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_160k.yml b/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_160k.yml index 46ec9d5916..b6604ec23b 100644 --- a/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_160k.yml +++ b/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_160k.yml @@ -14,7 +14,7 @@ model: backbone_indices: [0] optimizer: - type: sgd + type: SGD lr_scheduler: type: PolynomialDecay diff --git a/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_40k.yml b/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_40k.yml index 3afc798f0d..dbf2ae3017 100644 --- a/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_40k.yml +++ b/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_40k.yml @@ -14,7 +14,7 @@ model: backbone_indices: [0] optimizer: - type: sgd + type: SGD lr_scheduler: type: PolynomialDecay diff --git a/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_40k_SCL.yml b/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_40k_SCL.yml index 894c22efa6..f86da8c34c 100644 --- a/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_40k_SCL.yml +++ b/configs/ocrnet/ocrnet_hrnetw48_cityscapes_1024x512_40k_SCL.yml @@ -14,7 +14,7 @@ model: backbone_indices: [0] optimizer: - type: sgd + type: SGD lr_scheduler: type: PolynomialDecay diff --git a/configs/pfpn/pfpn_resnet101_os8_cityscapes_512x1024_40k.yml b/configs/pfpn/pfpn_resnet101_os8_cityscapes_512x1024_40k.yml index 986b0e0c02..fcff33b997 100644 --- a/configs/pfpn/pfpn_resnet101_os8_cityscapes_512x1024_40k.yml +++ b/configs/pfpn/pfpn_resnet101_os8_cityscapes_512x1024_40k.yml @@ -34,6 +34,6 @@ lr_scheduler: power: 0.9 optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0005 diff --git a/configs/pointrend/pointrend_resnet50_os8_cityscapes_1024x512_80k.yml b/configs/pointrend/pointrend_resnet50_os8_cityscapes_1024x512_80k.yml index f462292691..2bba475d97 100644 --- a/configs/pointrend/pointrend_resnet50_os8_cityscapes_1024x512_80k.yml +++ b/configs/pointrend/pointrend_resnet50_os8_cityscapes_1024x512_80k.yml @@ -18,6 +18,6 @@ loss: optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0005 diff --git a/configs/pointrend/pointrend_resnet50_os8_voc12aug_512x512_40k.yml b/configs/pointrend/pointrend_resnet50_os8_voc12aug_512x512_40k.yml index 9702543615..cac044597e 100644 --- a/configs/pointrend/pointrend_resnet50_os8_voc12aug_512x512_40k.yml +++ b/configs/pointrend/pointrend_resnet50_os8_voc12aug_512x512_40k.yml @@ -18,6 +18,6 @@ loss: optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0005 diff --git a/configs/portraitnet/portraitnet_eg1800_224x224_46k.yml b/configs/portraitnet/portraitnet_eg1800_224x224_46k.yml index 9703b8ad6b..e9eb9b999f 100644 --- a/configs/portraitnet/portraitnet_eg1800_224x224_46k.yml +++ b/configs/portraitnet/portraitnet_eg1800_224x224_46k.yml @@ -49,7 +49,7 @@ val_dataset: mode: val optimizer: - type: adam + type: Adam weight_decay: 5.0e-4 lr_scheduler: diff --git a/configs/pp_humanseg_lite/pp_humanseg_lite_export_398x224.yml b/configs/pp_humanseg_lite/pp_humanseg_lite_export_398x224.yml index a80633291a..689f94da32 100644 --- a/configs/pp_humanseg_lite/pp_humanseg_lite_export_398x224.yml +++ b/configs/pp_humanseg_lite/pp_humanseg_lite_export_398x224.yml @@ -4,12 +4,6 @@ model: align_corners: False num_classes: 2 -export: - transforms: - - type: Resize - target_size: [398, 224] - - type: Normalize - val_dataset: type: Dataset dataset_root: data/mini_supervisely diff --git a/configs/pp_humanseg_lite/pp_humanseg_lite_mini_supervisely.yml b/configs/pp_humanseg_lite/pp_humanseg_lite_mini_supervisely.yml index f7034daa29..a64acaf03d 100644 --- a/configs/pp_humanseg_lite/pp_humanseg_lite_mini_supervisely.yml +++ b/configs/pp_humanseg_lite/pp_humanseg_lite_mini_supervisely.yml @@ -28,14 +28,8 @@ val_dataset: - type: Normalize mode: val -export: - transforms: - - type: Resize - target_size: [398, 224] - - type: Normalize - optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0005 diff --git a/configs/pp_liteseg/pp_liteseg_stdc1_camvid_960x720_10k.yml b/configs/pp_liteseg/pp_liteseg_stdc1_camvid_960x720_10k.yml index e4cfe5ceaa..97980438b8 100644 --- a/configs/pp_liteseg/pp_liteseg_stdc1_camvid_960x720_10k.yml +++ b/configs/pp_liteseg/pp_liteseg_stdc1_camvid_960x720_10k.yml @@ -31,7 +31,7 @@ val_dataset: - type: Normalize optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 5.0e-4 diff --git a/configs/pssl/pp_liteseg_stdc1_pssl.yml b/configs/pssl/pp_liteseg_stdc1_pssl.yml index 84fde853ff..76fe581826 100644 --- a/configs/pssl/pp_liteseg_stdc1_pssl.yml +++ b/configs/pssl/pp_liteseg_stdc1_pssl.yml @@ -28,7 +28,7 @@ train_dataset: mode: train optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 5.0e-4 diff --git a/configs/pssl/stdc1_seg_pssl.yml b/configs/pssl/stdc1_seg_pssl.yml index 1357946b81..3d661ba19c 100644 --- a/configs/pssl/stdc1_seg_pssl.yml +++ b/configs/pssl/stdc1_seg_pssl.yml @@ -28,7 +28,7 @@ train_dataset: mode: train optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/quick_start/bisenet_optic_disc_512x512_1k.yml b/configs/quick_start/bisenet_optic_disc_512x512_1k.yml index 9bc5096ab8..7db1c7235a 100644 --- a/configs/quick_start/bisenet_optic_disc_512x512_1k.yml +++ b/configs/quick_start/bisenet_optic_disc_512x512_1k.yml @@ -19,7 +19,7 @@ val_dataset: mode: val optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/quick_start/deeplabv3p_resnet18_os8_optic_disc_512x512_1k_student.yml b/configs/quick_start/deeplabv3p_resnet18_os8_optic_disc_512x512_1k_student.yml index 6f3db4860c..2f06d43ce6 100644 --- a/configs/quick_start/deeplabv3p_resnet18_os8_optic_disc_512x512_1k_student.yml +++ b/configs/quick_start/deeplabv3p_resnet18_os8_optic_disc_512x512_1k_student.yml @@ -21,7 +21,7 @@ val_dataset: mode: val optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/quick_start/deeplabv3p_resnet50_os8_optic_disc_512x512_1k_teacher.yml b/configs/quick_start/deeplabv3p_resnet50_os8_optic_disc_512x512_1k_teacher.yml index f3434a33b9..071280e34f 100644 --- a/configs/quick_start/deeplabv3p_resnet50_os8_optic_disc_512x512_1k_teacher.yml +++ b/configs/quick_start/deeplabv3p_resnet50_os8_optic_disc_512x512_1k_teacher.yml @@ -21,7 +21,7 @@ val_dataset: mode: val optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/quick_start/pp_liteseg_optic_disc_512x512_1k.yml b/configs/quick_start/pp_liteseg_optic_disc_512x512_1k.yml index 54859cf5f0..bc894427c9 100644 --- a/configs/quick_start/pp_liteseg_optic_disc_512x512_1k.yml +++ b/configs/quick_start/pp_liteseg_optic_disc_512x512_1k.yml @@ -31,7 +31,7 @@ val_dataset: - type: Normalize optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 4.0e-5 diff --git a/configs/rtformer/rtformer_base_ade20k_512x512_160k.yml b/configs/rtformer/rtformer_base_ade20k_512x512_160k.yml index 8f94d6e08c..9c4efedbb8 100644 --- a/configs/rtformer/rtformer_base_ade20k_512x512_160k.yml +++ b/configs/rtformer/rtformer_base_ade20k_512x512_160k.yml @@ -29,16 +29,6 @@ val_dataset: - type: Normalize mean: [0.485, 0.456, 0.406] std: [0.229, 0.224, 0.225] - -export: - transforms: - - type: Resize - target_size: [2048, 512] - keep_ratio: True - size_divisor: 32 - - type: Normalize - mean: [0.485, 0.456, 0.406] - std: [0.229, 0.224, 0.225] optimizer: _inherited_: False diff --git a/configs/rtformer/rtformer_base_cityscapes_1024x512_120k.yml b/configs/rtformer/rtformer_base_cityscapes_1024x512_120k.yml index a982745fc3..b16bbf8314 100644 --- a/configs/rtformer/rtformer_base_cityscapes_1024x512_120k.yml +++ b/configs/rtformer/rtformer_base_cityscapes_1024x512_120k.yml @@ -28,15 +28,6 @@ val_dataset: - type: Normalize mean: [0.485, 0.456, 0.406] std: [0.229, 0.224, 0.225] - -export: - transforms: - - type: Resize - target_size: [2048, 512] - keep_ratio: True - - type: Normalize - mean: [0.485, 0.456, 0.406] - std: [0.229, 0.224, 0.225] optimizer: _inherited_: False diff --git a/configs/rtformer/rtformer_slim_ade20k_512x512_160k.yml b/configs/rtformer/rtformer_slim_ade20k_512x512_160k.yml index 5fa550b557..b541d24cf1 100644 --- a/configs/rtformer/rtformer_slim_ade20k_512x512_160k.yml +++ b/configs/rtformer/rtformer_slim_ade20k_512x512_160k.yml @@ -29,16 +29,6 @@ val_dataset: - type: Normalize mean: [0.485, 0.456, 0.406] std: [0.229, 0.224, 0.225] - -export: - transforms: - - type: Resize - target_size: [2048, 512] - keep_ratio: True - size_divisor: 32 - - type: Normalize - mean: [0.485, 0.456, 0.406] - std: [0.229, 0.224, 0.225] optimizer: _inherited_: False diff --git a/configs/rtformer/rtformer_slim_cityscapes_1024x512_120k.yml b/configs/rtformer/rtformer_slim_cityscapes_1024x512_120k.yml index 8539b825f2..15a14026b0 100644 --- a/configs/rtformer/rtformer_slim_cityscapes_1024x512_120k.yml +++ b/configs/rtformer/rtformer_slim_cityscapes_1024x512_120k.yml @@ -28,15 +28,6 @@ val_dataset: - type: Normalize mean: [0.485, 0.456, 0.406] std: [0.229, 0.224, 0.225] - -export: - transforms: - - type: Resize - target_size: [2048, 512] - keep_ratio: True - - type: Normalize - mean: [0.485, 0.456, 0.406] - std: [0.229, 0.224, 0.225] optimizer: _inherited_: False diff --git a/configs/sfnet/sfnet_resnet18_os8_cityscapes_1024x1024_80k.yml b/configs/sfnet/sfnet_resnet18_os8_cityscapes_1024x1024_80k.yml index c0d1f9b873..ec7ad7ab83 100644 --- a/configs/sfnet/sfnet_resnet18_os8_cityscapes_1024x1024_80k.yml +++ b/configs/sfnet/sfnet_resnet18_os8_cityscapes_1024x1024_80k.yml @@ -32,6 +32,6 @@ loss: coef: [1] optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 0.0005 diff --git a/configs/smrt/base_cfg.yml b/configs/smrt/base_cfg.yml index f1ffbd5851..cda225377b 100644 --- a/configs/smrt/base_cfg.yml +++ b/configs/smrt/base_cfg.yml @@ -31,7 +31,7 @@ val_dataset: - type: Normalize optimizer: - type: sgd + type: SGD momentum: 0.9 weight_decay: 5.0e-4 diff --git a/configs/topformer/topformer_base_ade20k_512x512_160k.yml b/configs/topformer/topformer_base_ade20k_512x512_160k.yml index e1a1338c62..c657b1d83b 100644 --- a/configs/topformer/topformer_base_ade20k_512x512_160k.yml +++ b/configs/topformer/topformer_base_ade20k_512x512_160k.yml @@ -30,16 +30,6 @@ val_dataset: mean: [0.485, 0.456, 0.406] std: [0.229, 0.224, 0.225] -export: - transforms: - - type: Resize - target_size: [2048, 512] - keep_ratio: True - size_divisor: 32 - - type: Normalize - mean: [0.485, 0.456, 0.406] - std: [0.229, 0.224, 0.225] - optimizer: _inherited_: False type: AdamW diff --git a/configs/topformer/topformer_small_ade20k_512x512_160k.yml b/configs/topformer/topformer_small_ade20k_512x512_160k.yml index 03c872e9b3..9856731023 100644 --- a/configs/topformer/topformer_small_ade20k_512x512_160k.yml +++ b/configs/topformer/topformer_small_ade20k_512x512_160k.yml @@ -29,16 +29,6 @@ val_dataset: - type: Normalize mean: [0.485, 0.456, 0.406] std: [0.229, 0.224, 0.225] - -export: - transforms: - - type: Resize - target_size: [2048, 512] - keep_ratio: True - size_divisor: 32 - - type: Normalize - mean: [0.485, 0.456, 0.406] - std: [0.229, 0.224, 0.225] optimizer: _inherited_: False diff --git a/configs/topformer/topformer_tiny_ade20k_512x512_160k.yml b/configs/topformer/topformer_tiny_ade20k_512x512_160k.yml index 8856775dea..c46df25a4c 100644 --- a/configs/topformer/topformer_tiny_ade20k_512x512_160k.yml +++ b/configs/topformer/topformer_tiny_ade20k_512x512_160k.yml @@ -29,16 +29,6 @@ val_dataset: - type: Normalize mean: [0.485, 0.456, 0.406] std: [0.229, 0.224, 0.225] - -export: - transforms: - - type: Resize - target_size: [2048, 512] - keep_ratio: True - size_divisor: 32 - - type: Normalize - mean: [0.485, 0.456, 0.406] - std: [0.229, 0.224, 0.225] optimizer: _inherited_: False diff --git a/configs/upernet/upernet_resnet101_os8_cityscapes_512x1024_40k.yml b/configs/upernet/upernet_resnet101_os8_cityscapes_512x1024_40k.yml index c95652253b..60276aebbf 100644 --- a/configs/upernet/upernet_resnet101_os8_cityscapes_512x1024_40k.yml +++ b/configs/upernet/upernet_resnet101_os8_cityscapes_512x1024_40k.yml @@ -15,7 +15,7 @@ model: enable_auxiliary_loss: True optimizer: - type: sgd + type: SGD weight_decay: 0.0005 loss: diff --git a/paddleseg/__init__.py b/paddleseg/__init__.py index f5d34517d0..ecddaf2216 100644 --- a/paddleseg/__init__.py +++ b/paddleseg/__init__.py @@ -12,6 +12,6 @@ # See the License for the specific language governing permissions and # limitations under the License. -from . import models, datasets, transforms +from . import models, datasets, transforms, optimizers __version__ = 'develop' diff --git a/paddleseg/cvlibs/callbacks.py b/paddleseg/cvlibs/callbacks.py deleted file mode 100644 index 1188b2cdac..0000000000 --- a/paddleseg/cvlibs/callbacks.py +++ /dev/null @@ -1,279 +0,0 @@ -# Copyright (c) 2020 PaddlePaddle Authors. All Rights Reserved. -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. - -import os -import time - -import numpy as np -import paddle -from paddle.distributed.parallel import ParallelEnv -from visualdl import LogWriter -from paddleseg.utils.progbar import Progbar -import paddleseg.utils.logger as logger - - -class CallbackList(object): - """ - Container abstracting a list of callbacks. - - Args: - callbacks (list[Callback]): List of `Callback` instances. - """ - - def __init__(self, callbacks=None): - callbacks = callbacks or [] - self.callbacks = [c for c in callbacks] - - def append(self, callback): - self.callbacks.append(callback) - - def set_params(self, params): - for callback in self.callbacks: - callback.set_params(params) - - def set_model(self, model): - for callback in self.callbacks: - callback.set_model(model) - - def set_optimizer(self, optimizer): - for callback in self.callbacks: - callback.set_optimizer(optimizer) - - def on_iter_begin(self, iter, logs=None): - """Called right before processing a batch. - """ - logs = logs or {} - for callback in self.callbacks: - callback.on_iter_begin(iter, logs) - self._t_enter_iter = time.time() - - def on_iter_end(self, iter, logs=None): - """Called at the end of a batch. - """ - logs = logs or {} - for callback in self.callbacks: - callback.on_iter_end(iter, logs) - self._t_exit_iter = time.time() - - def on_train_begin(self, logs=None): - """Called at the beginning of training. - """ - logs = logs or {} - for callback in self.callbacks: - callback.on_train_begin(logs) - - def on_train_end(self, logs=None): - """Called at the end of training. - """ - logs = logs or {} - for callback in self.callbacks: - callback.on_train_end(logs) - - def __iter__(self): - return iter(self.callbacks) - - -class Callback(object): - """Abstract base class used to build new callbacks. - """ - - def __init__(self): - self.validation_data = None - - def set_params(self, params): - self.params = params - - def set_model(self, model): - self.model = model - - def set_optimizer(self, optimizer): - self.optimizer = optimizer - - def on_iter_begin(self, iter, logs=None): - pass - - def on_iter_end(self, iter, logs=None): - pass - - def on_train_begin(self, logs=None): - pass - - def on_train_end(self, logs=None): - pass - - -class BaseLogger(Callback): - def __init__(self, period=10): - super(BaseLogger, self).__init__() - self.period = period - - def _reset(self): - self.totals = {} - - def on_train_begin(self, logs=None): - self.totals = {} - - def on_iter_end(self, iter, logs=None): - logs = logs or {} - #(iter - 1) // iters_per_epoch + 1 - for k, v in logs.items(): - if k in self.totals.keys(): - self.totals[k] += v - else: - self.totals[k] = v - - if iter % self.period == 0 and ParallelEnv().local_rank == 0: - - for k in self.totals: - logs[k] = self.totals[k] / self.period - self._reset() - - -class TrainLogger(Callback): - def __init__(self, log_freq=10): - self.log_freq = log_freq - - def _calculate_eta(self, remaining_iters, speed): - if remaining_iters < 0: - remaining_iters = 0 - remaining_time = int(remaining_iters * speed) - result = "{:0>2}:{:0>2}:{:0>2}" - arr = [] - for i in range(2, -1, -1): - arr.append(int(remaining_time / 60**i)) - remaining_time %= 60**i - return result.format(*arr) - - def on_iter_end(self, iter, logs=None): - - if iter % self.log_freq == 0 and ParallelEnv().local_rank == 0: - total_iters = self.params["total_iters"] - iters_per_epoch = self.params["iters_per_epoch"] - remaining_iters = total_iters - iter - eta = self._calculate_eta(remaining_iters, logs["batch_cost"]) - current_epoch = (iter - 1) // self.params["iters_per_epoch"] + 1 - loss = logs["loss"] - lr = self.optimizer.get_lr() - batch_cost = logs["batch_cost"] - reader_cost = logs["reader_cost"] - - logger.info( - "[TRAIN] epoch={}, iter={}/{}, loss={:.4f}, lr={:.6f}, batch_cost={:.4f}, reader_cost={:.4f} | ETA {}" - .format(current_epoch, iter, total_iters, loss, lr, batch_cost, - reader_cost, eta)) - - -class ProgbarLogger(Callback): - def __init__(self): - super(ProgbarLogger, self).__init__() - - def on_train_begin(self, logs=None): - self.verbose = self.params["verbose"] - self.total_iters = self.params["total_iters"] - self.target = self.params["total_iters"] - self.progbar = Progbar(target=self.target, verbose=self.verbose) - self.seen = 0 - self.log_values = [] - - def on_iter_begin(self, iter, logs=None): - #self.seen = 0 - if self.seen < self.target: - self.log_values = [] - - def on_iter_end(self, iter, logs=None): - logs = logs or {} - self.seen += 1 - for k in self.params['metrics']: - if k in logs: - self.log_values.append((k, logs[k])) - - #if self.verbose and self.seen < self.target and ParallelEnv.local_rank == 0: - #print(self.log_values) - if self.seen < self.target: - self.progbar.update(self.seen, self.log_values) - - -class ModelCheckpoint(Callback): - def __init__(self, - save_dir, - monitor="miou", - save_best_only=False, - save_params_only=True, - mode="max", - period=1): - - super(ModelCheckpoint, self).__init__() - self.monitor = monitor - self.save_dir = save_dir - self.save_best_only = save_best_only - self.save_params_only = save_params_only - self.period = period - self.iters_since_last_save = 0 - - if mode == "min": - self.monitor_op = np.less - self.best = np.Inf - elif mode == "max": - self.monitor_op = np.greater - self.best = -np.Inf - else: - raise RuntimeError("`mode` is neither \"min\" nor \"max\"!") - - def on_train_begin(self, logs=None): - self.verbose = self.params["verbose"] - save_dir = self.save_dir - if not os.path.isdir(save_dir): - if os.path.exists(save_dir): - os.remove(save_dir) - os.makedirs(save_dir) - - def on_iter_end(self, iter, logs=None): - logs = logs or {} - self.iters_since_last_save += 1 - current_save_dir = os.path.join(self.save_dir, "iter_{}".format(iter)) - current_save_dir = os.path.abspath(current_save_dir) - #if self.iters_since_last_save % self.period and ParallelEnv().local_rank == 0: - #self.iters_since_last_save = 0 - if iter % self.period == 0 and ParallelEnv().local_rank == 0: - if self.verbose > 0: - print("iter {iter_num}: saving model to {path}".format( - iter_num=iter, path=current_save_dir)) - - paddle.save(self.model.state_dict(), - os.path.join(current_save_dir, 'model.pdparams')) - - if not self.save_params_only: - paddle.save(self.optimizer.state_dict(), - os.path.join(current_save_dir, 'model.pdopt')) - - -class VisualDL(Callback): - def __init__(self, log_dir="./log", freq=1): - super(VisualDL, self).__init__() - self.log_dir = log_dir - self.freq = freq - - def on_train_begin(self, logs=None): - self.writer = LogWriter(self.log_dir) - - def on_iter_end(self, iter, logs=None): - logs = logs or {} - if iter % self.freq == 0 and ParallelEnv().local_rank == 0: - for k, v in logs.items(): - self.writer.add_scalar("Train/{}".format(k), v, iter) - - self.writer.flush() - - def on_train_end(self, logs=None): - self.writer.close() diff --git a/paddleseg/cvlibs/config.py b/paddleseg/cvlibs/config.py index 2a0f1ebf4f..e6fc0c263f 100644 --- a/paddleseg/cvlibs/config.py +++ b/paddleseg/cvlibs/config.py @@ -112,25 +112,35 @@ def __str__(self) -> str: #################### hyper parameters @cached_property def batch_size(self) -> int: - return self.dic.get('batch_size', 1) + return self.dic.get('batch_size') @cached_property def iters(self) -> int: - iters = self.dic.get('iters', None) - if iters is None: - raise RuntimeError('No iters specified in the configuration file.') - return iters + return self.dic.get('iters') @cached_property def to_static_training(self) -> bool: - '''Whether to use @to_static for training''' return self.dic.get('to_static_training', False) #################### lr_scheduler and optimizer + @cached_property + def optimizer(self) -> paddle.optimizer.Optimizer: + opt_cfg = self.dic.get('optimizer').copy() + # For compatibility + if opt_cfg['type'] == 'adam': + opt_cfg['type'] = 'Adam' + if opt_cfg['type'] == 'sgd': + opt_cfg['type'] = 'SGD' + if opt_cfg['type'] == 'SGD' and 'momentum' in opt_cfg: + opt_cfg['type'] = 'Momentum' + opt = self.builder.create_object(opt_cfg) + opt = opt(self.model, self.lr_scheduler) + return opt + @cached_property def lr_scheduler(self) -> paddle.optimizer.lr.LRScheduler: assert 'lr_scheduler' in self.dic, 'No `lr_scheduler` specified in the configuration file.' - params = self.dic.get('lr_scheduler') + params = self.dic.get('lr_scheduler').copy() use_warmup = False if 'warmup_iters' in params: @@ -159,51 +169,6 @@ def lr_scheduler(self) -> paddle.optimizer.lr.LRScheduler: return lr_sche - @cached_property - def optimizer_config(self) -> dict: - args = self.dic.get('optimizer', {}).copy() - # TODO remove the default params - if args['type'] == 'sgd': - args.setdefault('momentum', 0.9) - return args - - @cached_property - def optimizer(self) -> paddle.optimizer.Optimizer: - lr = self.lr_scheduler - args = self.optimizer_config - optimizer_type = args.pop('type') - - # TODO refactor optimizer to support customized setting - params = self.model.parameters() - if 'backbone_lr_mult' in args: - if not hasattr(self.model, 'backbone'): - logger.warning('The backbone_lr_mult is not effective because' - ' the model does not have backbone') - else: - backbone_lr_mult = args.pop('backbone_lr_mult') - backbone_params = self.model.backbone.parameters() - backbone_params_id = [id(x) for x in backbone_params] - other_params = [ - x for x in params if id(x) not in backbone_params_id - ] - params = [{ - 'params': backbone_params, - 'learning_rate': backbone_lr_mult - }, { - 'params': other_params - }] - - if optimizer_type == 'sgd': - return paddle.optimizer.Momentum(lr, parameters=params, **args) - elif optimizer_type == 'adam': - return paddle.optimizer.Adam(lr, parameters=params, **args) - elif optimizer_type in paddle.optimizer.__all__: - return getattr(paddle.optimizer, optimizer_type)(lr, - parameters=params, - **args) - - raise RuntimeError('Unknown optimizer type {}.'.format(optimizer_type)) - #################### loss @cached_property def loss(self) -> dict: @@ -214,14 +179,6 @@ def distill_loss(self) -> dict: return self._prepare_loss('distill_loss') def _prepare_loss(self, loss_name): - """ - Parse the loss parameters and load the loss layers. - - Args: - loss_name (str): The root name of loss in the yaml file. - Returns: - dict: A dict including the loss parameters and layers. - """ args = self.dic.get(loss_name, {}).copy() losses = {'coef': args['coef'], "types": []} for loss_cfg in args['types']: @@ -236,58 +193,44 @@ def model(self) -> paddle.nn.Layer: #################### dataset and transforms @cached_property - def train_dataset_config(self) -> Dict: - return self.dic.get('train_dataset', {}).copy() + def train_dataset(self) -> paddle.io.Dataset: + dataset_cfg = self.dic.get('train_dataset').copy() + return self.builder.create_object(dataset_cfg) @cached_property - def val_dataset_config(self) -> Dict: - return self.dic.get('val_dataset', {}).copy() + def val_dataset(self) -> paddle.io.Dataset: + assert 'val_dataset' in self.dic, \ + 'No val_dataset specified in the configuration file.' + dataset_cfg = self.dic.get('val_dataset').copy() + return self.builder.create_object(dataset_cfg) @cached_property def train_dataset_class(self) -> Any: - dataset_type = self.train_dataset_config['type'] + dataset_type = self.dic['train_dataset']['type'] return self.builder.load_component_class(dataset_type) @cached_property def val_dataset_class(self) -> Any: - dataset_type = self.val_dataset_config['type'] + assert 'val_dataset' in self.dic, \ + 'No val_dataset specified in the configuration file.' + dataset_type = self.dic['val_dataset']['type'] return self.builder.load_component_class(dataset_type) - @cached_property - def train_dataset(self) -> paddle.io.Dataset: - _train_dataset = self.train_dataset_config - if not _train_dataset: - return None - return self.builder.create_object(_train_dataset) - - @cached_property - def val_dataset(self) -> paddle.io.Dataset: - _val_dataset = self.val_dataset_config - if not _val_dataset: - return None - return self.builder.create_object(_val_dataset) - @cached_property def val_transforms(self) -> list: - """Get val_transform from val_dataset""" - _val_dataset = self.val_dataset_config - if not _val_dataset: - return [] - _transforms = _val_dataset.get('transforms', []) transforms = [] - for tf in _transforms: - transforms.append(self.builder.create_object(tf)) + if 'val_dataset' in self.dic: + for tf in self.dic.get('val_dataset').get('transforms', []): + transforms.append(self.builder.create_object(tf)) return transforms - #################### test and export @cached_property - def test_config(self) -> Dict: - return self.dic.get('test_config', {}) + def val_dataset_config(self) -> Dict: + return self.dic.get('val_dataset', {}).copy() - # TODO remove export_config @cached_property - def export_config(self) -> Dict: - return self.dic.get('export', {}) + def test_config(self) -> Dict: + return self.dic.get('test_config', {}).copy() #################### checker and builder @classmethod @@ -317,7 +260,7 @@ def _build_default_checker(cls): def _build_default_component_builder(cls): com_list = [ manager.MODELS, manager.BACKBONES, manager.DATASETS, - manager.TRANSFORMS, manager.LOSSES + manager.TRANSFORMS, manager.LOSSES, manager.OPTIMIZERS ] component_builder = builder.DefaultComponentBuilder(com_list=com_list) return component_builder diff --git a/paddleseg/cvlibs/config_checker.py b/paddleseg/cvlibs/config_checker.py index 98e366cb3b..694bc503fb 100644 --- a/paddleseg/cvlibs/config_checker.py +++ b/paddleseg/cvlibs/config_checker.py @@ -14,6 +14,8 @@ import copy +from paddleseg.utils import logger + class ConfigChecker(object): """ @@ -62,10 +64,13 @@ def apply(self, cfg, allow_update): class DefaultPrimaryRule(Rule): def check_and_correct(self, cfg): - assert cfg.dic.get('model', None) is not None, \ - 'No model specified in the configuration file.' - assert cfg.train_dataset_config or cfg.val_dataset_config, \ - 'One of `train_dataset` or `val_dataset should be given, but there are none.' + items = [ + 'batch_size', 'iters', 'train_dataset', 'optimizer', 'lr_scheduler', + 'loss', 'model' + ] + for i in items: + assert i in cfg.dic, \ + 'No {} specified in the configuration file.'.format(i) class DefaultLossRule(Rule): @@ -94,77 +99,69 @@ def check_and_correct(self, cfg): class DefaultSyncNumClassesRule(Rule): def check_and_correct(self, cfg): - num_classes_set = set() - - if cfg.dic['model'].get('num_classes', None) is not None: - num_classes_set.add(cfg.dic['model'].get('num_classes')) - if cfg.train_dataset_config: - if hasattr(cfg.train_dataset_class, 'NUM_CLASSES'): - num_classes_set.add(cfg.train_dataset_class.NUM_CLASSES) - if 'num_classes' in cfg.train_dataset_config: - num_classes_set.add(cfg.train_dataset_config['num_classes']) - if cfg.val_dataset_config: - if hasattr(cfg.val_dataset_class, 'NUM_CLASSES'): - num_classes_set.add(cfg.val_dataset_class.NUM_CLASSES) - if 'num_classes' in cfg.val_dataset_config: - num_classes_set.add(cfg.val_dataset_config['num_classes']) - - if len(num_classes_set) == 0: + model_config = cfg.dic['model'] + train_dataset_config = cfg.dic['train_dataset'] + val_dataset_config = cfg.dic['val_dataset'] + value_set = set() + value_name = 'num_classes' + + if value_name in model_config: + value_set.add(model_config[value_name]) + if value_name in train_dataset_config: + value_set.add(train_dataset_config[value_name]) + if value_name in val_dataset_config: + value_set.add(val_dataset_config[value_name]) + if hasattr(cfg.train_dataset_class, 'NUM_CLASSES'): + value_set.add(cfg.train_dataset_class.NUM_CLASSES) + if hasattr(cfg.val_dataset_class, 'NUM_CLASSES'): + value_set.add(cfg.val_dataset_class.NUM_CLASSES) + + if len(value_set) == 0: raise ValueError( '`num_classes` is not found. Please set it in model, train_dataset or val_dataset' ) - elif len(num_classes_set) > 1: + elif len(value_set) > 1: raise ValueError( '`num_classes` is not consistent: {}. Please set it consistently in model or train_dataset or val_dataset' - .format(num_classes_set)) + .format(value_set)) - num_classes = num_classes_set.pop() - cfg.dic['model']['num_classes'] = num_classes - if cfg.train_dataset_config and \ - (not hasattr(cfg.train_dataset_class, 'NUM_CLASSES')): - cfg.dic['train_dataset']['num_classes'] = num_classes - if cfg.val_dataset_config and \ - (not hasattr(cfg.val_dataset_class, 'NUM_CLASSES')): - cfg.dic['val_dataset']['num_classes'] = num_classes + model_config[value_name] = value_set.pop() class DefaultSyncImgChannelsRule(Rule): def check_and_correct(self, cfg): - img_channels_set = set() - model_cfg = cfg.dic['model'] + model_config = cfg.dic['model'] + train_dataset_config = cfg.dic['train_dataset'] + val_dataset_config = cfg.dic['val_dataset'] + value_set = set() # If the model has backbone, in_channels is the input params of backbone. # Otherwise, in_channels is the input params of the model. - if 'backbone' in model_cfg: - x = model_cfg['backbone'].get('in_channels', None) + if 'backbone' in model_config: + x = model_config['backbone'].get('in_channels', None) if x is not None: - img_channels_set.add(x) - elif model_cfg.get('in_channels', None) is not None: - img_channels_set.add(model_cfg.get('in_channels')) - if cfg.train_dataset_config and \ - ('img_channels' in cfg.train_dataset_config): - img_channels_set.add(cfg.train_dataset_config['img_channels']) - if cfg.val_dataset_config and \ - ('img_channels' in cfg.val_dataset_config): - img_channels_set.add(cfg.val_dataset_config['img_channels']) - - if len(img_channels_set) > 1: + value_set.add(x) + if 'in_channels' in model_config: + value_set.add(model_config['in_channels']) + if 'img_channels' in train_dataset_config: + value_set.add(train_dataset_config['img_channels']) + if 'img_channels' in val_dataset_config: + value_set.add(val_dataset_config['img_channels']) + if hasattr(cfg.train_dataset_class, 'IMG_CHANNELS'): + value_set.add(cfg.train_dataset_class.IMG_CHANNELS) + if hasattr(cfg.val_dataset_class, 'IMG_CHANNELS'): + value_set.add(cfg.val_dataset_class.IMG_CHANNELS) + + if len(value_set) > 1: raise ValueError( - '`img_channels` is not consistent: {}. Please set it consistently in model or train_dataset or val_dataset' - .format(img_channels_set)) + '`in_channels` is not consistent: {}. Please set it consistently in model or train_dataset or val_dataset' + .format(value_set)) + channels = 3 if len(value_set) == 0 else value_set.pop() - img_channels = 3 if len(img_channels_set) == 0 \ - else img_channels_set.pop() - if 'backbone' in model_cfg: - cfg.dic['model']['backbone']['in_channels'] = img_channels + if 'backbone' in model_config: + model_config['backbone']['in_channels'] = channels else: - cfg.dic['model']['in_channels'] = img_channels - if cfg.train_dataset_config and \ - cfg.train_dataset_config['type'] == "Dataset": - cfg.dic['train_dataset']['img_channels'] = img_channels - if cfg.val_dataset_config and \ - cfg.val_dataset_config['type'] == "Dataset": - cfg.dic['val_dataset']['img_channels'] = img_channels + model_config['in_channels'] = channels class DefaultSyncIgnoreIndexRule(Rule): @@ -178,17 +175,36 @@ def _check_ignore_index(loss_cfg, dataset_ignore_index): assert loss_cfg['ignore_index'] == dataset_ignore_index, \ 'the ignore_index in loss and train_dataset must be the same. Currently, loss ignore_index = {}, '\ 'train_dataset ignore_index = {}'.format(loss_cfg['ignore_index'], dataset_ignore_index) + else: + loss_cfg['ignore_index'] = dataset_ignore_index loss_cfg = cfg.dic.get(self.loss_name, None) if loss_cfg is None: return - dataset_ignore_index = cfg.train_dataset.ignore_index + train_dataset_config = cfg.dic['train_dataset'] + val_dataset_config = cfg.dic['val_dataset'] + value_set = set() + value_name = 'ignore_index' + + if value_name in train_dataset_config: + value_set.add(train_dataset_config[value_name]) + if value_name in val_dataset_config: + value_set.add(val_dataset_config[value_name]) + if hasattr(cfg.train_dataset_class, 'IGNORE_INDEX'): + value_set.add(cfg.train_dataset_class.IGNORE_INDEX) + if hasattr(cfg.val_dataset_class, 'IGNORE_INDEX'): + value_set.add(cfg.val_dataset_class.IGNORE_INDEX) + + if len(value_set) > 1: + raise ValueError( + '`ignore_index` is not consistent: {}. Please set it consistently in train_dataset and val_dataset' + .format(value_set)) + ignore_index = 255 if len(value_set) == 0 else value_set.pop() + for loss_cfg_i in loss_cfg['types']: if loss_cfg_i['type'] == 'MixedLoss': for loss_cfg_j in loss_cfg_i['losses']: - _check_ignore_index(loss_cfg_j, dataset_ignore_index) - loss_cfg_j['ignore_index'] = dataset_ignore_index + _check_ignore_index(loss_cfg_j, ignore_index) else: - _check_ignore_index(loss_cfg_i, dataset_ignore_index) - loss_cfg_i['ignore_index'] = dataset_ignore_index + _check_ignore_index(loss_cfg_i, ignore_index) diff --git a/paddleseg/cvlibs/manager.py b/paddleseg/cvlibs/manager.py index 8437445ac0..8a3ee6a024 100644 --- a/paddleseg/cvlibs/manager.py +++ b/paddleseg/cvlibs/manager.py @@ -145,3 +145,4 @@ def add_component(self, components): DATASETS = ComponentManager("datasets") TRANSFORMS = ComponentManager("transforms") LOSSES = ComponentManager("losses") +OPTIMIZERS = ComponentManager("optimizers") diff --git a/paddleseg/datasets/ade.py b/paddleseg/datasets/ade.py index 8a9a2e9324..ce36b87aba 100644 --- a/paddleseg/datasets/ade.py +++ b/paddleseg/datasets/ade.py @@ -39,6 +39,8 @@ class ADE20K(Dataset): edge (bool, optional): Whether to compute edge while training. Default: False """ NUM_CLASSES = 150 + IGNORE_INDEX = 255 + IMG_CHANNELS = 3 def __init__(self, transforms, dataset_root=None, mode='train', edge=False): self.dataset_root = dataset_root @@ -47,7 +49,7 @@ def __init__(self, transforms, dataset_root=None, mode='train', edge=False): self.mode = mode self.file_list = list() self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX self.edge = edge if mode not in ['train', 'val']: diff --git a/paddleseg/datasets/chase_db1.py b/paddleseg/datasets/chase_db1.py index 1b2538025b..ef43ecfccb 100644 --- a/paddleseg/datasets/chase_db1.py +++ b/paddleseg/datasets/chase_db1.py @@ -39,6 +39,8 @@ class CHASEDB1(Dataset): mode (str, optional): Which part of dataset to use. it is one of ('train', 'val', 'test'). Default: 'train'. """ NUM_CLASSES = 2 + IGNORE_INDEX = 255 + IMG_CHANNELS = 3 def __init__(self, dataset_root=None, @@ -52,7 +54,7 @@ def __init__(self, self.edge = edge self.file_list = list() self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 # labels only have 1/0, thus ignore_index is not necessary + self.ignore_index = self.IGNORE_INDEX # labels only have 1/0, thus ignore_index is not necessary if mode not in ['train', 'val', 'test']: raise ValueError( diff --git a/paddleseg/datasets/cityscapes.py b/paddleseg/datasets/cityscapes.py index 564926e384..7488b8487d 100644 --- a/paddleseg/datasets/cityscapes.py +++ b/paddleseg/datasets/cityscapes.py @@ -47,6 +47,8 @@ class Cityscapes(Dataset): edge (bool, optional): Whether to compute edge while training. Default: False """ NUM_CLASSES = 19 + IGNORE_INDEX = 255 + IMG_CHANNELS = 3 def __init__(self, transforms, dataset_root, mode='train', edge=False): self.dataset_root = dataset_root @@ -55,7 +57,7 @@ def __init__(self, transforms, dataset_root, mode='train', edge=False): mode = mode.lower() self.mode = mode self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX self.edge = edge if mode not in ['train', 'val', 'test']: diff --git a/paddleseg/datasets/cocostuff.py b/paddleseg/datasets/cocostuff.py index ae66461d5e..bbb69a519c 100644 --- a/paddleseg/datasets/cocostuff.py +++ b/paddleseg/datasets/cocostuff.py @@ -44,6 +44,8 @@ class CocoStuff(Dataset): edge (bool, optional): Whether to compute edge while training. Default: False """ NUM_CLASSES = 171 + IGNORE_INDEX = 255 + IMG_CHANNELS = 3 def __init__(self, transforms, dataset_root, mode='train', edge=False): self.dataset_root = dataset_root @@ -52,7 +54,7 @@ def __init__(self, transforms, dataset_root, mode='train', edge=False): mode = mode.lower() self.mode = mode self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX self.edge = edge if mode not in ['train', 'val']: diff --git a/paddleseg/datasets/drive.py b/paddleseg/datasets/drive.py index 8984aa005b..dcd924d854 100644 --- a/paddleseg/datasets/drive.py +++ b/paddleseg/datasets/drive.py @@ -37,6 +37,8 @@ class DRIVE(Dataset): mode (str, optional): Which part of dataset to use. it is one of ('train', 'val', 'test'). Default: 'train'. """ NUM_CLASSES = 2 + IGNORE_INDEX = 255 + IMG_CHANNELS = 3 def __init__(self, dataset_root=None, @@ -50,7 +52,7 @@ def __init__(self, self.edge = edge self.file_list = list() self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 # labels only have 1/0, thus ignore_index is not necessary + self.ignore_index = self.IGNORE_INDEX # labels only have 1/0, thus ignore_index is not necessary if mode not in ['train', 'val', 'test']: raise ValueError( diff --git a/paddleseg/datasets/eg1800.py b/paddleseg/datasets/eg1800.py index 9005083a92..1d6ff764cf 100644 --- a/paddleseg/datasets/eg1800.py +++ b/paddleseg/datasets/eg1800.py @@ -42,6 +42,8 @@ class EG1800(Dataset): edge (bool, optional): Whether to compute edge while training. Default: False """ NUM_CLASSES = 2 + IGNORE_INDEX = 255 + IMG_CHANNELS = 3 def __init__(self, common_transforms, @@ -58,7 +60,7 @@ def __init__(self, if transforms2 is not None: self.transforms2 = Compose(transforms2, to_rgb=False) mode = mode.lower() - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX self.mode = mode self.num_classes = self.NUM_CLASSES self.input_width = 224 diff --git a/paddleseg/datasets/hrf.py b/paddleseg/datasets/hrf.py index fb378a72c3..c4d89217f3 100644 --- a/paddleseg/datasets/hrf.py +++ b/paddleseg/datasets/hrf.py @@ -36,6 +36,8 @@ class HRF(Dataset): mode (str, optional): Which part of dataset to use. it is one of ('train', 'val', 'test'). Default: 'train'. """ NUM_CLASSES = 2 + IGNORE_INDEX = 255 + IMG_CHANNELS = 3 def __init__(self, dataset_root=None, @@ -49,7 +51,7 @@ def __init__(self, self.edge = edge self.file_list = list() self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX if mode not in ['train', 'val', 'test']: raise ValueError( diff --git a/paddleseg/datasets/mini_deep_globe_road_extraction.py b/paddleseg/datasets/mini_deep_globe_road_extraction.py index 7180a9dbe5..43249d46e1 100644 --- a/paddleseg/datasets/mini_deep_globe_road_extraction.py +++ b/paddleseg/datasets/mini_deep_globe_road_extraction.py @@ -37,6 +37,8 @@ class MiniDeepGlobeRoadExtraction(Dataset): edge (bool, optional): Whether to compute edge while training. Default: False. """ NUM_CLASSES = 2 + IGNORE_INDEX = 255 + IMG_CHANNELS = 3 def __init__(self, dataset_root=None, @@ -49,7 +51,7 @@ def __init__(self, self.mode = mode self.file_list = list() self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX self.edge = edge if mode not in ['train', 'val']: diff --git a/paddleseg/datasets/optic_disc_seg.py b/paddleseg/datasets/optic_disc_seg.py index 36332b085e..60040ba7e8 100644 --- a/paddleseg/datasets/optic_disc_seg.py +++ b/paddleseg/datasets/optic_disc_seg.py @@ -36,6 +36,8 @@ class OpticDiscSeg(Dataset): edge (bool, optional): Whether to compute edge while training. Default: False """ NUM_CLASSES = 2 + IGNORE_INDEX = 255 + IMG_CHANNELS = 3 def __init__(self, dataset_root=None, @@ -48,7 +50,7 @@ def __init__(self, self.mode = mode self.file_list = list() self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX self.edge = edge if mode not in ['train', 'val', 'test']: diff --git a/paddleseg/datasets/pascal_context.py b/paddleseg/datasets/pascal_context.py index fd362eea29..950c7fb46f 100644 --- a/paddleseg/datasets/pascal_context.py +++ b/paddleseg/datasets/pascal_context.py @@ -34,6 +34,8 @@ class PascalContext(Dataset): edge (bool, optional): Whether to compute edge while training. Default: False """ NUM_CLASSES = 60 + IGNORE_INDEX = 255 + IMG_CHANNELS = 3 def __init__(self, transforms=None, @@ -46,7 +48,7 @@ def __init__(self, self.mode = mode self.file_list = list() self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX self.edge = edge if mode not in ['train', 'trainval', 'val']: diff --git a/paddleseg/datasets/pp_humanseg14k.py b/paddleseg/datasets/pp_humanseg14k.py index e809611975..755f4a36ea 100644 --- a/paddleseg/datasets/pp_humanseg14k.py +++ b/paddleseg/datasets/pp_humanseg14k.py @@ -36,6 +36,8 @@ class PPHumanSeg14K(Dataset): edge (bool, optional): Whether to compute edge while training. Default: False. """ NUM_CLASSES = 2 + IGNORE_INDEX = 255 + IMG_CHANNELS = 3 def __init__(self, dataset_root=None, @@ -48,7 +50,7 @@ def __init__(self, self.mode = mode self.file_list = list() self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX self.edge = edge if mode not in ['train', 'val', 'test']: diff --git a/paddleseg/datasets/pssl.py b/paddleseg/datasets/pssl.py index 1066ce3280..ee28405176 100644 --- a/paddleseg/datasets/pssl.py +++ b/paddleseg/datasets/pssl.py @@ -71,6 +71,8 @@ class PSSLDataset(Dataset): """ ignore_index = 1001 # 0~999 is target class, 1000 is bg NUM_CLASSES = 1001 # consider target class and bg + IGNORE_INDEX = 1001 + IMG_CHANNELS = 3 def __init__(self, transforms, @@ -89,7 +91,7 @@ def __init__(self, self.edge = edge self.num_classes = self.NUM_CLASSES - self.ignore_index = self.num_classes # 1001 + self.ignore_index = self.IGNORE_INDEX # 1001 self.file_list = [] self.class_id_dict = {} diff --git a/paddleseg/datasets/stare.py b/paddleseg/datasets/stare.py index 5de8be58c3..5c5093a396 100644 --- a/paddleseg/datasets/stare.py +++ b/paddleseg/datasets/stare.py @@ -36,6 +36,8 @@ class STARE(Dataset): mode (str, optional): Which part of dataset to use. it is one of ('train', 'val', 'test'). Default: 'train'. """ NUM_CLASSES = 2 + IGNORE_INDEX = 1001 + IMG_CHANNELS = 3 def __init__(self, dataset_root=None, @@ -49,7 +51,7 @@ def __init__(self, self.edge = edge self.file_list = list() self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX if mode not in ['train', 'val', 'test']: raise ValueError( diff --git a/paddleseg/datasets/supervisely.py b/paddleseg/datasets/supervisely.py index accfa465af..c8ff045f8b 100644 --- a/paddleseg/datasets/supervisely.py +++ b/paddleseg/datasets/supervisely.py @@ -42,6 +42,8 @@ class SUPERVISELY(Dataset): edge (bool, optional): Whether to compute edge while training. Default: False """ NUM_CLASSES = 2 + IGNORE_INDEX = 1001 + IMG_CHANNELS = 3 def __init__(self, common_transforms, @@ -58,7 +60,7 @@ def __init__(self, if transforms2 is not None: self.transforms2 = Compose(transforms2, to_rgb=False) mode = mode.lower() - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX self.mode = mode self.num_classes = self.NUM_CLASSES self.input_width = 224 diff --git a/paddleseg/datasets/voc.py b/paddleseg/datasets/voc.py index 5ddea42f94..b81b8ba1ec 100644 --- a/paddleseg/datasets/voc.py +++ b/paddleseg/datasets/voc.py @@ -37,6 +37,8 @@ class PascalVOC(Dataset): edge (bool, optional): Whether to compute edge while training. Default: False """ NUM_CLASSES = 21 + IGNORE_INDEX = 1001 + IMG_CHANNELS = 3 def __init__(self, transforms, dataset_root=None, mode='train', edge=False): self.dataset_root = dataset_root @@ -45,7 +47,7 @@ def __init__(self, transforms, dataset_root=None, mode='train', edge=False): self.mode = mode self.file_list = list() self.num_classes = self.NUM_CLASSES - self.ignore_index = 255 + self.ignore_index = self.IGNORE_INDEX self.edge = edge if mode not in ['train', 'trainval', 'trainaug', 'val']: diff --git a/paddleseg/models/hrnet_contrast.py b/paddleseg/models/hrnet_contrast.py index dd5a20640e..2d6d40988f 100644 --- a/paddleseg/models/hrnet_contrast.py +++ b/paddleseg/models/hrnet_contrast.py @@ -31,7 +31,7 @@ class HRNetW48Contrast(nn.Layer): (https://arxiv.org/abs/2101.11939). Args: - in_channels (int): The output dimensions of backbone. + bb_channels (int): The output dimensions of backbone. num_classes (int): The unique number of target classes. backbone (Paddle.nn.Layer): Backbone network, currently support HRNet_W48. drop_prob (float): The probability of dropout. @@ -42,7 +42,7 @@ class HRNetW48Contrast(nn.Layer): """ def __init__(self, - in_channels, + bb_channels, num_classes, backbone, drop_prob, @@ -50,7 +50,7 @@ def __init__(self, align_corners=False, pretrained=None): super().__init__() - self.in_channels = in_channels + self.bb_channels = bb_channels self.backbone = backbone self.num_classes = num_classes self.proj_dim = proj_dim @@ -58,16 +58,16 @@ def __init__(self, self.cls_head = nn.Sequential( layers.ConvBNReLU( - in_channels, in_channels, kernel_size=3, stride=1, padding=1), + bb_channels, bb_channels, kernel_size=3, stride=1, padding=1), nn.Dropout2D(drop_prob), nn.Conv2D( - in_channels, + bb_channels, num_classes, kernel_size=1, stride=1, bias_attr=False), ) self.proj_head = ProjectionHead( - dim_in=in_channels, proj_dim=self.proj_dim) + dim_in=bb_channels, proj_dim=self.proj_dim) self.pretrained = pretrained self.init_weight() diff --git a/paddleseg/optimizers/__init__.py b/paddleseg/optimizers/__init__.py new file mode 100644 index 0000000000..a51e52722c --- /dev/null +++ b/paddleseg/optimizers/__init__.py @@ -0,0 +1,14 @@ +# Copyright (c) 2022 PaddlePaddle Authors. All Rights Reserved. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and + +from .optimizer import * \ No newline at end of file diff --git a/paddleseg/optimizers/optimizer.py b/paddleseg/optimizers/optimizer.py new file mode 100644 index 0000000000..ab3adb7534 --- /dev/null +++ b/paddleseg/optimizers/optimizer.py @@ -0,0 +1,234 @@ +# Copyright (c) 2022 PaddlePaddle Authors. All Rights Reserved. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +import paddle + +from paddleseg.cvlibs import manager +from paddleseg.utils import logger + + +class BaseOptimizer(object): + """ + Base optimizer in PaddleSeg. + + Args: + weight_decay(float, optional): A float value as coeff of L2 regularization. + grad_clip_cfg(dict, optional): A dict to specify grad_clip. It must have the following format: + {'name': 'ClipGradByGlobalNorm', 'clip_norm': float_val}, + {'name': 'ClipGradByNorm', 'clip_norm': float_val}, + {'name': 'ClipGradByValue', 'max': float_val, 'min': float_val(optional)}. + custom_cfg(list, optional): custom_cfg specify different options for + different parameter groups such as the learning rate and weight decay. + For example, [{'name': 'backbone', 'lr_mult': 0.1}, {'name': 'norm', 'weight_decay_mult': 0}] + + An example in config: + ` + optimizer: + type: SGD + weight_decay: 4.0e-5 + custom_cfg: + - name: backbone + lr_mult: 0.1 + - name: norm + weight_decay_mult: 0.0 + grad_clip_cfg: + name: ClipGradByValue + max: 1.0 + ` + """ + + def __init__(self, weight_decay=None, grad_clip_cfg=None, custom_cfg=None): + if weight_decay is not None: + assert isinstance(weight_decay, float), \ + "`weight_decay` must be a float." + if grad_clip_cfg is not None: + assert isinstance(grad_clip_cfg, dict), \ + "`grad_clip_cfg` must be a dict." + assert 'name' in grad_clip_cfg, 'No name specified in grad_clip_cfg' + grad_clip_names = [ + 'ClipGradByValue', 'ClipGradByNorm', 'ClipGradByGlobalNorm' + ] + assert grad_clip_cfg['name'] in grad_clip_names, \ + 'grad_clip name should be {}'.format(grad_clip_names) + if custom_cfg is not None: + assert isinstance(custom_cfg, list), "`custom_cfg` must be a list." + for item in custom_cfg: + assert isinstance( + item, dict), "The item of `custom_cfg` must be a dict" + + self.weight_decay = weight_decay + self.custom_cfg = custom_cfg + self.args = {'weight_decay': weight_decay} + + if grad_clip_cfg is not None: + grad_clip_cfg = grad_clip_cfg.copy() + grad_clip_name = grad_clip_cfg.pop('name') + try: + grad_clip = getattr(paddle.nn, grad_clip_name)(**grad_clip_cfg) + except Exception as e: + raise RuntimeError( + "Create grad_clip has failed. Please check grad_clip_cfg in config. " + f"The error message: \n{str(e)}") + self.args.update({'grad_clip': grad_clip}) + + def __call__(self, model, lr): + # Create optimizer + pass + + def _collect_params(self, model): + # Collect different parameter groups + if self.custom_cfg is None or len(self.custom_cfg) == 0: + return model.parameters() + + groups_num = len(self.custom_cfg) + 1 + params_list = [[] for _ in range(groups_num)] + for name, param in model.named_parameters(): + if param.stop_gradient: + continue + for idx, item in enumerate(self.custom_cfg): + if item['name'] in name: + params_list[idx].append(param) + break + else: + params_list[-1].append(param) + + res = [] + for idx, item in enumerate(self.custom_cfg): + lr_mult = item.get("lr_mult", 1.0) + weight_decay_mult = item.get("weight_decay_mult", None) + param_dict = {'params': params_list[idx], 'learning_rate': lr_mult} + if self.weight_decay is not None and weight_decay_mult is not None: + param_dict[ + 'weight_decay'] = self.weight_decay * weight_decay_mult + res.append(param_dict) + res.append({'params': params_list[-1]}) + + msg = 'Parameter groups for optimizer: \n' + for idx, item in enumerate(self.custom_cfg): + params_name = [p.name for p in params_list[idx]] + item = item.copy() + item['params_name'] = params_name + msg += 'Group {}: \n{} \n'.format(idx, item) + msg += 'Last group:\n params_name: {}'.format( + [p.name for p in params_list[-1]]) + logger.info(msg) + + return res + + +@manager.OPTIMIZERS.add_component +class SGD(BaseOptimizer): + """ + SGD optimizer. + + An example in config: + ` + optimizer: + type: SGD + weight_decay: 4.0e-5 + custom_cfg: + - name: backbone + lr_mult: 0.1 + - name: norm + weight_decay_mult: 0.0 + ` + """ + + def __init__(self, weight_decay=None, grad_clip_cfg=None, custom_cfg=None): + super().__init__(weight_decay, grad_clip_cfg, custom_cfg) + + def __call__(self, model, lr): + params = self._collect_params(model) + return paddle.optimizer.SGD(learning_rate=lr, + parameters=params, + **self.args) + + +@manager.OPTIMIZERS.add_component +class Momentum(BaseOptimizer): + """ + Momentum optimizer. + """ + + def __init__(self, + momentum=0.9, + use_nesterov=False, + weight_decay=None, + grad_clip_cfg=None, + custom_cfg=None): + super().__init__(weight_decay, grad_clip_cfg, custom_cfg) + self.args.update({'momentum': momentum, 'use_nesterov': use_nesterov}) + + def __call__(self, model, lr): + params = self._collect_params(model) + return paddle.optimizer.Momentum( + learning_rate=lr, parameters=params, **self.args) + + +@manager.OPTIMIZERS.add_component +class Adam(BaseOptimizer): + """ + Adam optimizer. + """ + + def __init__(self, + beta1=0.9, + beta2=0.999, + epsilon=1e-08, + lazy_mode=False, + weight_decay=None, + grad_clip_cfg=None, + custom_cfg=None): + super().__init__(weight_decay, grad_clip_cfg, custom_cfg) + self.args.update({ + 'beta1': beta1, + 'beta2': beta2, + 'epsilon': epsilon, + 'lazy_mode': lazy_mode + }) + + def __call__(self, model, lr): + params = self._collect_params(model) + opt = paddle.optimizer.Adam( + learning_rate=lr, parameters=params, **self.args) + return opt + + +@manager.OPTIMIZERS.add_component +class AdamW(BaseOptimizer): + """ + AdamW optimizer. + """ + + def __init__(self, + beta1=0.9, + beta2=0.999, + epsilon=1e-08, + weight_decay=0.01, + lazy_mode=False, + grad_clip_cfg=None, + custom_cfg=None): + super().__init__(weight_decay, grad_clip_cfg, custom_cfg) + self.args.update({ + 'beta1': beta1, + 'beta2': beta2, + 'epsilon': epsilon, + 'lazy_mode': lazy_mode + }) + + def __call__(self, model, lr): + params = self._collect_params(model) + opt = paddle.optimizer.AdamW( + learning_rate=lr, parameters=params, **self.args) + return opt diff --git a/tools/export.py b/tools/export.py index a576b67576..b23032fc6d 100644 --- a/tools/export.py +++ b/tools/export.py @@ -25,7 +25,6 @@ def parse_args(): parser = argparse.ArgumentParser(description='Export Inference Model.') - parser.add_argument("--config", help="The path of config file.", type=str) parser.add_argument( '--model_path', @@ -36,7 +35,6 @@ def parse_args(): help='The directory for saving the exported inference model', type=str, default='./output/inference_model') - parser.add_argument( "--input_shape", nargs='+',