czczup / ViT-Adapter

[ICLR 2023 Spotlight] Vision Transformer Adapter for Dense Predictions
https://arxiv.org/abs/2205.08534
Apache License 2.0
1.22k stars 137 forks source link

你好,请问”assert (count_mat == 0).sum() == 0“,在文件中的作用是什么? #11

Closed 847001315 closed 2 years ago

847001315 commented 2 years ago

ViT-Adapter-main/segmentation/mmseg_custom/models/segmentors/encoder_decoder_mask2former.py的195行,存在句子”assert (count_mat == 0).sum() == 0“,每次运行都会因为这个异常而跳出来。我将其注释掉,程序可以正常运行,但每次得出来的结果都是一样的,不知道和这里是否有关?想请问,count_mat代表什么意思?

下面是那一段代码: def slide_inference(self, img, img_meta, rescale): """Inference by sliding-window with overlap.

    If h_crop > h_img or w_crop > w_img, the small patch will be used to
    decode without padding.
    """
    print("img.shape",img.shape)
    # print("img",img)
    h_stride, w_stride = self.test_cfg.stride
    h_crop, w_crop = self.test_cfg.crop_size
    batch_size, _, h_img, w_img = img.size()

    num_classes = self.num_classes
    # print("num_class",num_classes)

    h_grids = max(h_img - h_crop + h_stride - 1, 0) // h_stride + 1
    w_grids = max(w_img - w_crop + w_stride - 1, 0) // w_stride + 1
    preds = img.new_zeros((batch_size, num_classes, h_img, w_img))
    # print("preds",preds)
    count_mat = img.new_zeros((batch_size, 1, h_img, w_img))
    # print("count_mat",count_mat)
    for h_idx in range(h_grids):
        for w_idx in range(w_grids):
            y1 = h_idx * h_stride
            x1 = w_idx * w_stride
            y2 = min(y1 + h_crop, h_img)
            x2 = min(x1 + w_crop, w_img)
            y1 = max(y2 - h_crop, 0)
            x1 = max(x2 - w_crop, 0)
            crop_img = img[:, :, y1:y2, x1:x2]
            crop_seg_logit = self.encode_decode(crop_img, img_meta)
            preds += F.pad(crop_seg_logit,
                           (int(x1), int(preds.shape[3] - x2), int(y1),
                            int(preds.shape[2] - y2)))

            count_mat[:, :, y1:y2, x1:x2] += 1
            # print(count_mat[:, :, y1:y2, x1:x2])

    # assert (count_mat == 0).sum() == 0
    if torch.onnx.is_in_onnx_export():
        # cast count_mat to constant while exporting to ONNX
        count_mat = torch.from_numpy(
            count_mat.cpu().detach().numpy()).to(device=img.device)
    preds = preds / count_mat
    # preds = preds
    if rescale:
        preds = resize(
            preds,
            size=img_meta[0]['ori_shape'][:2],
            mode='bilinear',
            align_corners=self.align_corners,
            warning=False)
    return preds

打扰了~~~

czczup commented 2 years ago

你好,能提供一下具体的环境信息吗

847001315 commented 2 years ago

好的,以下是我的环境信息: cuda:10.2 pytorch:1.10 mmcv-full:1.4.4 mmsegmentation:0.20.2 mmdet:2.22.0 数据集说明:为自定义的医学数据集,其中包含一类目标类,其余被背景,图像尺寸为【112112,三通道】,mask图像为【112112,单通道,同时处理过,将背景的像素点的像素值设为0,目标类的像素点的像素值设为1】 其中数据集的自定义类文件为:


from mmseg.datasets.builder import DATASETS
from mmseg.datasets.custom import CustomDataset

@DATASETS.register_module()
class EchonetDataset(CustomDataset):
    ## 数据集标注的各类名称,即 0, 1, 2, 3... 各个类别的对应名称
    CLASSES = (
        'background','heart',
    )
    # # 各类类别的 BGR 三通道值,用于可视化预测结果
    PALETTE = [ [0, 0, 0],[255, 255, 255]]

    def __init__(self, **kwargs):
        super(EchonetDataset, self).__init__(
            img_suffix='.jpg',
            seg_map_suffix='.png',
            reduce_zero_label=False, ## 此时 label 里的 0(上面 CLASSES 里第一个 “label_a”)在计算损失函数和指标时不会被忽略。
            **kwargs
        )

最终生成的配置文件的config为如下:


num_things_classes = 2
num_stuff_classes = 0
num_classes = 2
norm_cfg = dict(type='SyncBN', requires_grad=True)
model = dict(
    type='EncoderDecoderMask2Former',
    pretrained=None,
    backbone=dict(
        type='BEiTAdapter',
        patch_size=16,
        embed_dim=1024,
        depth=24,
        num_heads=16,
        mlp_ratio=4,
        qkv_bias=True,
        use_abs_pos_emb=False,
        use_rel_pos_bias=True,
        img_size=224,
        init_values=1e-06,
        drop_path_rate=0.3,
        conv_inplane=64,
        n_points=4,
        deform_num_heads=16,
        cffn_ratio=0.25,
        deform_ratio=0.5,
        interaction_indexes=[[0, 5], [6, 11], [12, 17], [18, 23]]),
    decode_head=dict(
        type='Mask2FormerHead',
        in_channels=[1024, 1024, 1024, 1024],
        feat_channels=1024,
        out_channels=1024,
        in_index=[0, 1, 2, 3],
        num_things_classes=2,
        num_stuff_classes=0,
        num_queries=100,
        num_transformer_feat_level=3,
        pixel_decoder=dict(
            type='MSDeformAttnPixelDecoder',
            num_outs=3,
            norm_cfg=dict(type='GN', num_groups=32),
            act_cfg=dict(type='ReLU'),
            encoder=dict(
                type='DetrTransformerEncoder',
                num_layers=6,
                transformerlayers=dict(
                    type='BaseTransformerLayer',
                    attn_cfgs=dict(
                        type='MultiScaleDeformableAttention',
                        embed_dims=1024,
                        num_heads=32,
                        num_levels=3,
                        num_points=4,
                        im2col_step=64,
                        dropout=0.0,
                        batch_first=False,
                        norm_cfg=None,
                        init_cfg=None),
                    ffn_cfgs=dict(
                        type='FFN',
                        embed_dims=1024,
                        feedforward_channels=4096,
                        num_fcs=2,
                        ffn_drop=0.0,
                        act_cfg=dict(type='ReLU', inplace=True)),
                    operation_order=('self_attn', 'norm', 'ffn', 'norm')),
                init_cfg=None),
            positional_encoding=dict(
                type='SinePositionalEncoding', num_feats=512, normalize=True),
            init_cfg=None),
        enforce_decoder_input_project=False,
        positional_encoding=dict(
            type='SinePositionalEncoding', num_feats=512, normalize=True),
        transformer_decoder=dict(
            type='DetrTransformerDecoder',
            return_intermediate=True,
            num_layers=9,
            transformerlayers=dict(
                type='DetrTransformerDecoderLayer',
                attn_cfgs=dict(
                    type='MultiheadAttention',
                    embed_dims=1024,
                    num_heads=32,
                    attn_drop=0.0,
                    proj_drop=0.0,
                    dropout_layer=None,
                    batch_first=False),
                ffn_cfgs=dict(
                    embed_dims=1024,
                    feedforward_channels=4096,
                    num_fcs=2,
                    act_cfg=dict(type='ReLU', inplace=True),
                    ffn_drop=0.0,
                    dropout_layer=None,
                    add_identity=True),
                feedforward_channels=4096,
                operation_order=('cross_attn', 'norm', 'self_attn', 'norm',
                                 'ffn', 'norm')),
            init_cfg=None),
        loss_cls=dict(
            type='CrossEntropyLoss',
            use_sigmoid=False,
            loss_weight=2.0,
            reduction='mean',
            class_weight=[1.0, 1.0, 0.1]),
        loss_mask=dict(
            type='CrossEntropyLoss',
            use_sigmoid=True,
            reduction='mean',
            loss_weight=5.0),
        loss_dice=dict(
            type='DiceLoss',
            use_sigmoid=True,
            activate=True,
            reduction='mean',
            naive_dice=True,
            eps=1.0,
            loss_weight=5.0)),
    train_cfg=dict(
        num_points=12544,
        oversample_ratio=3.0,
        importance_sample_ratio=0.75,
        assigner=dict(
            type='MaskHungarianAssigner',
            cls_cost=dict(type='ClassificationCost', weight=2.0),
            mask_cost=dict(
                type='CrossEntropyLossCost', weight=5.0, use_sigmoid=True),
            dice_cost=dict(
                type='DiceCost', weight=5.0, pred_act=True, eps=1.0)),
        sampler=dict(type='MaskPseudoSampler')),
    test_cfg=dict(
        panoptic_on=True,
        semantic_on=False,
        instance_on=True,
        max_per_image=100,
        iou_thr=0.8,
        filter_low_score=True,
        mode='slide',
        crop_size=(224, 224),
        stride=(426, 426)),
    init_cfg=None)
find_unused_parameters = True
dataset_type = 'EchonetDataset'
data_root = '/data/cgh/project/ViT-Adapter-main/segmentation/data/echonet_dataset'
img_norm_cfg = dict(
    mean=[123.675, 116.28, 103.53], std=[58.395, 57.12, 57.375], to_rgb=True)
crop_size = (224, 224)
train_pipeline = [
    dict(type='LoadImageFromFile'),
    dict(type='LoadAnnotations', reduce_zero_label=True),
    dict(type='RandomFlip', prob=0.5),
    dict(type='PhotoMetricDistortion'),
    dict(
        type='Normalize',
        mean=[123.675, 116.28, 103.53],
        std=[58.395, 57.12, 57.375],
        to_rgb=True),
    dict(type='Pad', size=(224, 224), pad_val=0, seg_pad_val=255),
    dict(type='ToMask'),
    dict(type='DefaultFormatBundle'),
    dict(
        type='Collect',
        keys=['img', 'gt_semantic_seg', 'gt_masks', 'gt_labels'])
]
test_pipeline = [
    dict(type='LoadImageFromFile'),
    dict(
        type='MultiScaleFlipAug',
        img_scale=(224, 224),
        flip=True,
        transforms=[
            dict(
                type='SETR_Resize',
                keep_ratio=True,
                crop_size=(224, 224),
                setr_multi_scale=True),
            dict(
                type='Normalize',
                mean=[123.675, 116.28, 103.53],
                std=[58.395, 57.12, 57.375],
                to_rgb=True),
            dict(type='ImageToTensor', keys=['img']),
            dict(type='Collect', keys=['img'])
        ])
]
data = dict(
    samples_per_gpu=1,
    workers_per_gpu=4,
    train=dict(
        type='EchonetDataset',
        data_root=
        '/data/cgh/project/ViT-Adapter-main/segmentation/data/echonet_dataset',
        img_dir='images/train',
        ann_dir='ann/train',
        pipeline=[
            dict(type='LoadImageFromFile'),
            dict(type='LoadAnnotations', reduce_zero_label=True),
            dict(type='RandomFlip', prob=0.5),
            dict(type='PhotoMetricDistortion'),
            dict(
                type='Normalize',
                mean=[123.675, 116.28, 103.53],
                std=[58.395, 57.12, 57.375],
                to_rgb=True),
            dict(type='Pad', size=(224, 224), pad_val=0, seg_pad_val=255),
            dict(type='ToMask'),
            dict(type='DefaultFormatBundle'),
            dict(
                type='Collect',
                keys=['img', 'gt_semantic_seg', 'gt_masks', 'gt_labels'])
        ]),
    val=dict(
        type='EchonetDataset',
        data_root=
        '/data/cgh/project/ViT-Adapter-main/segmentation/data/echonet_dataset',
        img_dir='images/val',
        ann_dir='ann/val',
        pipeline=[
            dict(type='LoadImageFromFile'),
            dict(
                type='MultiScaleFlipAug',
                img_scale=(224, 224),
                flip=True,
                transforms=[
                    dict(
                        type='SETR_Resize',
                        keep_ratio=True,
                        crop_size=(224, 224),
                        setr_multi_scale=True),
                    dict(
                        type='Normalize',
                        mean=[123.675, 116.28, 103.53],
                        std=[58.395, 57.12, 57.375],
                        to_rgb=True),
                    dict(type='ImageToTensor', keys=['img']),
                    dict(type='Collect', keys=['img'])
                ])
        ]),
    test=dict(
        type='EchonetDataset',
        data_root=
        '/data/cgh/project/ViT-Adapter-main/segmentation/data/echonet_dataset',
        img_dir='images/test',
        ann_dir='ann/test',
        pipeline=[
            dict(type='LoadImageFromFile'),
            dict(
                type='MultiScaleFlipAug',
                img_scale=(224, 224),
                flip=True,
                transforms=[
                    dict(
                        type='SETR_Resize',
                        keep_ratio=True,
                        crop_size=(224, 224),
                        setr_multi_scale=True),
                    dict(
                        type='Normalize',
                        mean=[123.675, 116.28, 103.53],
                        std=[58.395, 57.12, 57.375],
                        to_rgb=True),
                    dict(type='ImageToTensor', keys=['img']),
                    dict(type='Collect', keys=['img'])
                ])
        ]))
log_config = dict(
    interval=50, hooks=[dict(type='TextLoggerHook', by_epoch=False)])
dist_params = dict(backend='nccl')
log_level = 'INFO'
load_from = None
resume_from = None
workflow = [('train', 1)]
cudnn_benchmark = True
optimizer = dict(
    type='AdamW',
    lr=2e-05,
    betas=(0.9, 0.999),
    weight_decay=0.05,
    constructor='LayerDecayOptimizerConstructor',
    paramwise_cfg=dict(num_layers=24, layer_decay_rate=0.9))
optimizer_config = dict()
lr_config = dict(
    policy='poly',
    warmup='linear',
    warmup_iters=1500,
    warmup_ratio=1e-06,
    power=1.0,
    min_lr=0.0,
    by_epoch=False)
runner = dict(type='IterBasedRunner', max_iters=160000)
checkpoint_config = dict(by_epoch=False, interval=1000, max_keep_ckpts=1)
evaluation = dict(
    interval=1600, metric='mIoU', pre_eval=True, save_best='mIoU')
t_size = 224
work_dir = './work_dirs/mask2former_beit_adapter_echonet'
gpu_ids = range(0, 1)
auto_resume = False

如果有需要,我可以把dataset和module的config继续贴上来,其中module就直接引用的本仓库的mask2former_beit.py。

在我没有修改除了config以外的情况下,代码无法跑通,会在我准备进行验证时出错,会在mmseg_custom/models/segmentors/EncoderDecoderMask2Former.py的第192行左右,即 assert (count_mat == 0).sum() == 0 处跳出异常。 具体代码如下:【除了注释了一句,其它并无修改】

# Copyright (c) OpenMMLab. All rights reserved.
import torch
import torch.nn as nn
import torch.nn.functional as F
from mmseg.core import add_prefix
from mmseg.models import builder
from mmseg.models.builder import SEGMENTORS
from mmseg.models.segmentors.base import BaseSegmentor
from mmseg.ops import resize

@SEGMENTORS.register_module()
class EncoderDecoderMask2Former(BaseSegmentor):
    """Encoder Decoder segmentors.

    EncoderDecoder typically consists of backbone, decode_head, auxiliary_head.
    Note that auxiliary_head is only used for deep supervision during training,
    which could be dumped during inference.
    """
    def __init__(self,
                 backbone,
                 decode_head,
                 neck=None,
                 auxiliary_head=None,
                 train_cfg=None,
                 test_cfg=None,
                 pretrained=None,
                 init_cfg=None):
        super(EncoderDecoderMask2Former, self).__init__(init_cfg)
        if pretrained is not None:
            assert backbone.get('pretrained') is None, \
                'both backbone and segmentor set pretrained weight'
            backbone.pretrained = pretrained
        self.backbone = builder.build_backbone(backbone)
        if neck is not None:
            self.neck = builder.build_neck(neck)
        decode_head.update(train_cfg=train_cfg)
        decode_head.update(test_cfg=test_cfg)
        self._init_decode_head(decode_head)
        self._init_auxiliary_head(auxiliary_head)

        self.train_cfg = train_cfg
        self.test_cfg = test_cfg

        assert self.with_decode_head

    def _init_decode_head(self, decode_head):
        """Initialize ``decode_head``"""
        self.decode_head = builder.build_head(decode_head)
        self.align_corners = self.decode_head.align_corners
        self.num_classes = self.decode_head.num_classes

    def _init_auxiliary_head(self, auxiliary_head):
        """Initialize ``auxiliary_head``"""
        if auxiliary_head is not None:
            if isinstance(auxiliary_head, list):
                self.auxiliary_head = nn.ModuleList()
                for head_cfg in auxiliary_head:
                    self.auxiliary_head.append(builder.build_head(head_cfg))
            else:
                self.auxiliary_head = builder.build_head(auxiliary_head)

    def extract_feat(self, img):
        """Extract features from images."""
        x = self.backbone(img)
        if self.with_neck:
            x = self.neck(x)
        return x

    def encode_decode(self, img, img_metas):
        """Encode images with backbone and decode into a semantic segmentation
        map of the same size as input."""
        x = self.extract_feat(img)
        out = self._decode_head_forward_test(x, img_metas)
        out = resize(
            input=out,
            size=img.shape[2:],
            mode='bilinear',
            align_corners=self.align_corners)
        return out

    def _decode_head_forward_train(self, x, img_metas, gt_semantic_seg,
                                   **kwargs):
        """Run forward function and calculate loss for decode head in
        training."""
        losses = dict()
        loss_decode = self.decode_head.forward_train(x, img_metas,
                                                     gt_semantic_seg, **kwargs)

        losses.update(add_prefix(loss_decode, 'decode'))
        return losses

    def _decode_head_forward_test(self, x, img_metas):
        """Run forward function and calculate loss for decode head in
        inference."""
        seg_logits = self.decode_head.forward_test(x, img_metas, self.test_cfg)
        return seg_logits

    def _auxiliary_head_forward_train(self, x, img_metas, gt_semantic_seg):
        """Run forward function and calculate loss for auxiliary head in
        training."""
        losses = dict()
        if isinstance(self.auxiliary_head, nn.ModuleList):
            for idx, aux_head in enumerate(self.auxiliary_head):
                loss_aux = aux_head.forward_train(x, img_metas,
                                                  gt_semantic_seg,
                                                  self.train_cfg)
                losses.update(add_prefix(loss_aux, f'aux_{idx}'))
        else:
            loss_aux = self.auxiliary_head.forward_train(
                x, img_metas, gt_semantic_seg, self.train_cfg)
            losses.update(add_prefix(loss_aux, 'aux'))

        return losses

    def forward_dummy(self, img):
        """Dummy forward function."""
        seg_logit = self.encode_decode(img, None)

        return seg_logit

    def forward_train(self, img, img_metas, gt_semantic_seg, **kwargs):
        """Forward function for training.

        Args:
            img (Tensor): Input images.
            img_metas (list[dict]): List of image info dict where each dict
                has: 'img_shape', 'scale_factor', 'flip', and may also contain
                'filename', 'ori_shape', 'pad_shape', and 'img_norm_cfg'.
                For details on the values of these keys see
                `mmseg/datasets/pipelines/formatting.py:Collect`.
            gt_semantic_seg (Tensor): Semantic segmentation masks
                used if the architecture supports semantic segmentation task.

        Returns:
            dict[str, Tensor]: a dictionary of loss components
        """

        x = self.extract_feat(img)

        losses = dict()

        loss_decode = self._decode_head_forward_train(x, img_metas,
                                                      gt_semantic_seg,
                                                      **kwargs)
        losses.update(loss_decode)

        if self.with_auxiliary_head:
            loss_aux = self._auxiliary_head_forward_train(
                x, img_metas, gt_semantic_seg)
            losses.update(loss_aux)

        return losses

    # TODO refactor
    def slide_inference(self, img, img_meta, rescale):
        """Inference by sliding-window with overlap.

        If h_crop > h_img or w_crop > w_img, the small patch will be used to
        decode without padding.
        """
        # print("img.shape",img.shape)
        # print("img",img)
        h_stride, w_stride = self.test_cfg.stride
        h_crop, w_crop = self.test_cfg.crop_size
        batch_size, _, h_img, w_img = img.size()

        num_classes = self.num_classes
        # print("num_class",num_classes)

        h_grids = max(h_img - h_crop + h_stride - 1, 0) // h_stride + 1
        w_grids = max(w_img - w_crop + w_stride - 1, 0) // w_stride + 1
        preds = img.new_zeros((batch_size, num_classes, h_img, w_img))
        # print("preds",preds)
        count_mat = img.new_zeros((batch_size, 1, h_img, w_img))
        # print("count_mat",count_mat)
        for h_idx in range(h_grids):
            for w_idx in range(w_grids):
                y1 = h_idx * h_stride
                x1 = w_idx * w_stride
                y2 = min(y1 + h_crop, h_img)
                x2 = min(x1 + w_crop, w_img)
                y1 = max(y2 - h_crop, 0)
                x1 = max(x2 - w_crop, 0)
                crop_img = img[:, :, y1:y2, x1:x2]
                crop_seg_logit = self.encode_decode(crop_img, img_meta)
                preds += F.pad(crop_seg_logit,
                               (int(x1), int(preds.shape[3] - x2), int(y1),
                                int(preds.shape[2] - y2)))

                count_mat[:, :, y1:y2, x1:x2] += 1
                # print(count_mat[:, :, y1:y2, x1:x2])

        # assert (count_mat == 0).sum() == 0
        if torch.onnx.is_in_onnx_export():
            # cast count_mat to constant while exporting to ONNX
            count_mat = torch.from_numpy(
                count_mat.cpu().detach().numpy()).to(device=img.device)
        preds = preds / count_mat
        # preds = preds
        if rescale:
            preds = resize(
                preds,
                size=img_meta[0]['ori_shape'][:2],
                mode='bilinear',
                align_corners=self.align_corners,
                warning=False)
        return preds

    def whole_inference(self, img, img_meta, rescale):
        """Inference with full image."""

        seg_logit = self.encode_decode(img, img_meta)
        if rescale:
            # support dynamic shape for onnx
            if torch.onnx.is_in_onnx_export():
                size = img.shape[2:]
            else:
                size = img_meta[0]['ori_shape'][:2]
            seg_logit = resize(
                seg_logit,
                size=size,
                mode='bilinear',
                align_corners=self.align_corners,
                warning=False)

        return seg_logit

    def inference(self, img, img_meta, rescale):
        """Inference with slide/whole style.

        Args:
            img (Tensor): The input image of shape (N, 3, H, W).
            img_meta (dict): Image info dict where each dict has: 'img_shape',
                'scale_factor', 'flip', and may also contain
                'filename', 'ori_shape', 'pad_shape', and 'img_norm_cfg'.
                For details on the values of these keys see
                `mmseg/datasets/pipelines/formatting.py:Collect`.
            rescale (bool): Whether rescale back to original shape.

        Returns:
            Tensor: The output segmentation map.
        """

        assert self.test_cfg.mode in ['slide', 'whole']
        ori_shape = img_meta[0]['ori_shape']
        assert all(_['ori_shape'] == ori_shape for _ in img_meta)
        if self.test_cfg.mode == 'slide':
            seg_logit = self.slide_inference(img, img_meta, rescale)
        else:
            seg_logit = self.whole_inference(img, img_meta, rescale)
        output = F.softmax(seg_logit, dim=1)
        flip = img_meta[0]['flip']
        if flip:
            flip_direction = img_meta[0]['flip_direction']
            assert flip_direction in ['horizontal', 'vertical']
            if flip_direction == 'horizontal':
                output = output.flip(dims=(3,))
            elif flip_direction == 'vertical':
                output = output.flip(dims=(2,))

        return output

    def simple_test(self, img, img_meta, rescale=True):
        """Simple test with single image."""
        seg_logit = self.inference(img, img_meta, rescale)
        seg_pred = seg_logit.argmax(dim=1)
        if torch.onnx.is_in_onnx_export():
            # our inference backend only support 4D output
            seg_pred = seg_pred.unsqueeze(0)
            return seg_pred
        seg_pred = seg_pred.cpu().numpy()
        # unravel batch dim
        seg_pred = list(seg_pred)
        return seg_pred

    def aug_test(self, imgs, img_metas, rescale=True):
        """Test with augmentations.

        Only rescale=True is supported.
        """
        # aug_test rescale all imgs back to ori_shape for now
        assert rescale
        # to save memory, we get augmented seg logit inplace
        seg_logit = self.inference(imgs[0], img_metas[0], rescale)
        for i in range(1, len(imgs)):
            cur_seg_logit = self.inference(imgs[i], img_metas[i], rescale)
            seg_logit += cur_seg_logit
        seg_logit /= len(imgs)
        seg_pred = seg_logit.argmax(dim=1)
        seg_pred = seg_pred.cpu().numpy()
        # unravel batch dim
        seg_pred = list(seg_pred)
        return seg_pred

我将count_mat输出出来,可以看到里面并非都是0,对这句话不理解,于是试着直接将其注释,发现代码可以运行。

目前代码可以运行,但得出来的结果非常奇怪,只能得到 be88309976798cd111f846e9cdc4d16

目前不清楚到底是我注释了这个代码的缘故,还是我config哪里的配置没有写好。

问题:跑出来只有一个类的结果,另外一个类始终是0 情况1?:可能是由于我注释了assert (count_mat == 0).sum() == 0这句话,不理解这句话的意义,想询问一下count_mat是什么意思,是否会影响最终结果 情况2?:会不会因为我的config文件哪里写错了? 情况3?:会不会是我数据集的图像尺寸过小?【已经确定数据集有被载入】

我目前自己可以想到的情况就是以上三种~ 非常谢谢您~,这两天一直打扰您了

czczup commented 2 years ago

@duanduanduanyuchen 看一看config

847001315 commented 2 years ago

@duanduanduanyuchen 看一看config

您是叫他来看我的config吗?还是我去看他某个仓库的config?

czczup commented 2 years ago

我发现了一个可能的地方,如果背景类(0)也要参与计算的话,reduce_zero_label=True得改成False。 我看到你的Dataset类里设成False了,不过config里还是True

czczup commented 2 years ago

@duanduanduanyuchen 看一看config

您是叫他来看我的config吗?还是我去看他某个仓库的config?

是的,他会帮你看

czczup commented 2 years ago

还有一个地方,我看到你说图像是112x112的,你这里是直接pad到224x224吗,而不是resize到224x224. 可以把

test_cfg=dict(mode='slide', crop_size=(224, 224), stride=(426, 426))

改成

test_cfg=dict(mode='slide', crop_size=(224, 224), stride=(224, 224))

或者

test_cfg=dict(mode='whole')

试一试

czczup commented 2 years ago

现在训练和测试的pipeline应该没有对齐,训练时是112pad到224,测试时是112resize224,这可能会造成一些精度下降

duanduanduanyuchen commented 2 years ago

assert (count_mat == 0).sum() == 0 这段代码的含义是保证count_mat矩阵所有元素非0,count_mat矩阵是在测试的slide过程中的计数矩阵,目的在于对原图像进行切割、滑窗后进行测试的过程中,整张图片被滑窗完全覆盖。 根据你的config,在你的model变量中你设置的crop_size(224,224),在test_pipeline变量中设置的img_scale也为(224,224),建议你检查在该段报错代码中的img的形状大小是否为(224,224)

847001315 commented 2 years ago

现在训练和测试的pipeline应该没有对齐,训练时是112pad到224,测试时是112resize224,这可能会造成一些精度下降

非常感谢您替我解答~我去按照您的说法去更改一下,谢谢谢谢~~~

847001315 commented 2 years ago

assert (count_mat == 0).sum() == 0 这段代码的含义是保证count_mat矩阵所有元素非0,count_mat矩阵是在测试的slide过程中的计数矩阵,目的在于对原图像进行切割、滑窗后进行测试的过程中,整张图片被滑窗完全覆盖。 根据你的config,在你的model变量中你设置的crop_size(224,224),在test_pipeline变量中设置的img_scale也为(224,224),建议你检查在该段报错代码中的img的形状大小是否为(224,224)

明白了~,也谢谢您替我解答~我再去补充一下相关知识,修改一下你们说的配置问题,再看看~,谢谢谢谢大家百忙之中抽空给我解答

czczup commented 2 years ago

assert (count_mat == 0).sum() == 0 这段代码的含义是保证count_mat矩阵所有元素非0,count_mat矩阵是在测试的slide过程中的计数矩阵,目的在于对原图像进行切割、滑窗后进行测试的过程中,整张图片被滑窗完全覆盖。 根据你的config,在你的model变量中你设置的crop_size(224,224),在test_pipeline变量中设置的img_scale也为(224,224),建议你检查在该段报错代码中的img的形状大小是否为(224,224)

明白了~,也谢谢您替我解答~我再去补充一下相关知识,修改一下你们说的配置问题,再看看~,谢谢谢谢大家百忙之中抽空给我解答

我试了一下MMSeg自带的医学数据集CHASE_DB1,config如下,可以参考一下:

# Copyright (c) Shanghai AI Lab. All rights reserved.
_base_ = [
    '../_base_/models/upernet_beit.py',
    '../_base_/datasets/chase_db1.py',
    '../_base_/default_runtime.py',
    '../_base_/schedules/schedule_40k.py'
]
img_scale = (960, 999)
crop_size = (128, 128)
# pretrained = 'https://conversationhub.blob.core.windows.net/beit-share-public/beit/beit_large_patch16_224_pt22k_ft22k.pth'
pretrained = 'pretrained/beit_large_patch16_224_pt22k_ft22k.pth'
model = dict(
    pretrained=pretrained,
    backbone=dict(
        type='BEiTAdapter',
        img_size=128,
        patch_size=16,
        embed_dim=1024,
        depth=24,
        num_heads=16,
        mlp_ratio=4,
        qkv_bias=True,
        use_abs_pos_emb=False,
        use_rel_pos_bias=True,
        init_values=1e-6,
        drop_path_rate=0.3,
        conv_inplane=64,
        n_points=4,
        deform_num_heads=16,
        cffn_ratio=0.25,
        deform_ratio=0.5,
        interaction_indexes=[[0, 5], [6, 11], [12, 17], [18, 23]],
    ),
    decode_head=dict(
        in_channels=[1024, 1024, 1024, 1024],
        num_classes=2,
        channels=1024,
    ),
    auxiliary_head=dict(
        in_channels=1024,
        num_classes=2
    ),
    test_cfg = dict(mode='slide', crop_size=crop_size, stride=(85, 85))
)
img_norm_cfg = dict(
    mean=[123.675, 116.28, 103.53], std=[58.395, 57.12, 57.375], to_rgb=True)
train_pipeline = [
    dict(type='LoadImageFromFile'),
    dict(type='LoadAnnotations'),
    dict(type='Resize', img_scale=img_scale, ratio_range=(0.5, 2.0)),
    dict(type='RandomCrop', crop_size=crop_size, cat_max_ratio=0.75),
    dict(type='RandomFlip', prob=0.5),
    dict(type='PhotoMetricDistortion'),
    dict(type='Normalize', **img_norm_cfg),
    dict(type='Pad', size=crop_size, pad_val=0, seg_pad_val=255),
    dict(type='DefaultFormatBundle'),
    dict(type='Collect', keys=['img', 'gt_semantic_seg'])
]
test_pipeline = [
    dict(type='LoadImageFromFile'),
    dict(
        type='MultiScaleFlipAug',
        img_scale=img_scale,
        # img_ratios=[0.5, 0.75, 1.0, 1.25, 1.5, 1.75],
        flip=False,
        transforms=[
            dict(type='Resize', keep_ratio=True),
            dict(type='ResizeToMultiple', size_divisor=32),
            dict(type='RandomFlip'),
            dict(type='Normalize', **img_norm_cfg),
            dict(type='ImageToTensor', keys=['img']),
            dict(type='Collect', keys=['img']),
        ])
]
optimizer = dict(_delete_=True, type='AdamW', lr=2e-5, betas=(0.9, 0.999), weight_decay=0.05,
                 constructor='LayerDecayOptimizerConstructor',
                 paramwise_cfg=dict(num_layers=24, layer_decay_rate=0.90))
lr_config = dict(_delete_=True, policy='poly',
                 warmup='linear',
                 warmup_iters=1500,
                 warmup_ratio=1e-6,
                 power=1.0, min_lr=0.0, by_epoch=False)
data=dict(train=dict(pipeline=train_pipeline),
          val=dict(pipeline=test_pipeline),
          test=dict(pipeline=test_pipeline))
runner = dict(type='IterBasedRunner')
checkpoint_config = dict(by_epoch=False, interval=1000, max_keep_ckpts=1)
evaluation = dict(interval=4000, metric='mDice', save_best='mDice')
847001315 commented 2 years ago

assert (count_mat == 0).sum() == 0 这段代码的含义是保证count_mat矩阵所有元素非0,count_mat矩阵是在测试的slide过程中的计数矩阵,目的在于对原图像进行切割、滑窗后进行测试的过程中,整张图片被滑窗完全覆盖。 根据你的config,在你的model变量中你设置的crop_size(224,224),在test_pipeline变量中设置的img_scale也为(224,224),建议你检查在该段报错代码中的img的形状大小是否为(224,224)

明白了~,也谢谢您替我解答~我再去补充一下相关知识,修改一下你们说的配置问题,再看看~,谢谢谢谢大家百忙之中抽空给我解答

我试了一下MMSeg自带的医学数据集CHASE_DB1,config如下,可以参考一下:

# Copyright (c) Shanghai AI Lab. All rights reserved.
_base_ = [
    '../_base_/models/upernet_beit.py',
    '../_base_/datasets/chase_db1.py',
    '../_base_/default_runtime.py',
    '../_base_/schedules/schedule_40k.py'
]
img_scale = (960, 999)
crop_size = (128, 128)
# pretrained = 'https://conversationhub.blob.core.windows.net/beit-share-public/beit/beit_large_patch16_224_pt22k_ft22k.pth'
pretrained = 'pretrained/beit_large_patch16_224_pt22k_ft22k.pth'
model = dict(
    pretrained=pretrained,
    backbone=dict(
        type='BEiTAdapter',
        img_size=128,
        patch_size=16,
        embed_dim=1024,
        depth=24,
        num_heads=16,
        mlp_ratio=4,
        qkv_bias=True,
        use_abs_pos_emb=False,
        use_rel_pos_bias=True,
        init_values=1e-6,
        drop_path_rate=0.3,
        conv_inplane=64,
        n_points=4,
        deform_num_heads=16,
        cffn_ratio=0.25,
        deform_ratio=0.5,
        interaction_indexes=[[0, 5], [6, 11], [12, 17], [18, 23]],
    ),
    decode_head=dict(
        in_channels=[1024, 1024, 1024, 1024],
        num_classes=2,
        channels=1024,
    ),
    auxiliary_head=dict(
        in_channels=1024,
        num_classes=2
    ),
    test_cfg = dict(mode='slide', crop_size=crop_size, stride=(85, 85))
)
img_norm_cfg = dict(
    mean=[123.675, 116.28, 103.53], std=[58.395, 57.12, 57.375], to_rgb=True)
train_pipeline = [
    dict(type='LoadImageFromFile'),
    dict(type='LoadAnnotations'),
    dict(type='Resize', img_scale=img_scale, ratio_range=(0.5, 2.0)),
    dict(type='RandomCrop', crop_size=crop_size, cat_max_ratio=0.75),
    dict(type='RandomFlip', prob=0.5),
    dict(type='PhotoMetricDistortion'),
    dict(type='Normalize', **img_norm_cfg),
    dict(type='Pad', size=crop_size, pad_val=0, seg_pad_val=255),
    dict(type='DefaultFormatBundle'),
    dict(type='Collect', keys=['img', 'gt_semantic_seg'])
]
test_pipeline = [
    dict(type='LoadImageFromFile'),
    dict(
        type='MultiScaleFlipAug',
        img_scale=img_scale,
        # img_ratios=[0.5, 0.75, 1.0, 1.25, 1.5, 1.75],
        flip=False,
        transforms=[
            dict(type='Resize', keep_ratio=True),
            dict(type='ResizeToMultiple', size_divisor=32),
            dict(type='RandomFlip'),
            dict(type='Normalize', **img_norm_cfg),
            dict(type='ImageToTensor', keys=['img']),
            dict(type='Collect', keys=['img']),
        ])
]
optimizer = dict(_delete_=True, type='AdamW', lr=2e-5, betas=(0.9, 0.999), weight_decay=0.05,
                 constructor='LayerDecayOptimizerConstructor',
                 paramwise_cfg=dict(num_layers=24, layer_decay_rate=0.90))
lr_config = dict(_delete_=True, policy='poly',
                 warmup='linear',
                 warmup_iters=1500,
                 warmup_ratio=1e-6,
                 power=1.0, min_lr=0.0, by_epoch=False)
data=dict(train=dict(pipeline=train_pipeline),
          val=dict(pipeline=test_pipeline),
          test=dict(pipeline=test_pipeline))
runner = dict(type='IterBasedRunner')
checkpoint_config = dict(by_epoch=False, interval=1000, max_keep_ckpts=1)
evaluation = dict(interval=4000, metric='mDice', save_best='mDice')

非常感谢您还抽空写了一下config!!我昨天吸收你们的建议后,去更改了一下,代码已经可以成功运行,并且iou并不会为0了。不过我遇到了问题,目前跑出来的结果,iou仅为60(deeplabv3跑该数据集可以iou=90),loss一直无法下降,目前仅仅调整学习率暂时无法解决,我会去再排查一下是否是我的config或者数据增强出现问题,也会参考您现在发的config,再一次感谢您回复我,十分感谢!!

czczup commented 2 years ago

昨天的config里好像没有加载预训练权重pretrained=None,不知道你后来有没有加上? 在CHASE_DB1上的结果看着还可以(unet+deeplabv3 40k训完是89.5左右的mDice, link) 目前16k/40k(还没训完)的log是这样:

2022-06-20 16:02:21,580 - mmseg - INFO -
+------------+-------+-------+
|   Class    |  Dice |  Acc  |
+------------+-------+-------+
| background | 98.65 | 98.55 |
|   vessel   | 80.19 | 81.37 |
+------------+-------+-------+
2022-06-20 16:02:21,580 - mmseg - INFO - Summary:
2022-06-20 16:02:21,580 - mmseg - INFO -
+-------+-------+-------+
|  aAcc | mDice |  mAcc |
+-------+-------+-------+
| 97.47 | 89.42 | 89.96 |
+-------+-------+-------+
847001315 commented 2 years ago

昨天的config里好像没有加载预训练权重pretrained=None,不知道你后来有没有加上?

后面依旧没有加上,有一个疑惑,例如您刚刚给我发的config中的model的backbone的image_size为128,但预训练权重是224的,是否可以载入?我一开始感觉我的图像尺寸和model的backbone尺寸不同就没有加,后续可以去加一下。

czczup commented 2 years ago

昨天的config里好像没有加载预训练权重pretrained=None,不知道你后来有没有加上?

后面依旧没有加上,有一个疑惑,例如您刚刚给我发的config中的model的backbone的image_size为128,但预训练权重是224的,是否可以载入?我一开始感觉我的图像尺寸和model的backbone尺寸不同就没有加,后续可以去加一下。

可以载入的,finetune的分辨率可以和预训练不一致 这个模型比较大,医疗数据一般都比较少,如果不用预训练效果可能会比较差

847001315 commented 2 years ago

昨天的config里好像没有加载预训练权重pretrained=None,不知道你后来有没有加上?

后面依旧没有加上,有一个疑惑,例如您刚刚给我发的config中的model的backbone的image_size为128,但预训练权重是224的,是否可以载入?我一开始感觉我的图像尺寸和model的backbone尺寸不同就没有加,后续可以去加一下。

可以载入的,finetune的分辨率可以和预训练不一致 这个模型比较大,医疗数据一般都比较少,如果不用预训练效果可能会比较差

好的!我后续去试验一下,刚刚开始接触mmseg框架,很多基础不清晰,非常打扰!!再一次感谢您!!想问一个问题,我的图片大小为112*112,test的mode选择whole和slide是否有影响?哪个模式更适合小图?whole吗?

czczup commented 2 years ago

昨天的config里好像没有加载预训练权重pretrained=None,不知道你后来有没有加上?

后面依旧没有加上,有一个疑惑,例如您刚刚给我发的config中的model的backbone的image_size为128,但预训练权重是224的,是否可以载入?我一开始感觉我的图像尺寸和model的backbone尺寸不同就没有加,后续可以去加一下。

可以载入的,finetune的分辨率可以和预训练不一致 这个模型比较大,医疗数据一般都比较少,如果不用预训练效果可能会比较差

好的!我后续去试验一下,刚刚开始接触mmseg框架,很多基础不清晰,非常打扰!!再一次感谢您!!想问一个问题,我的图片大小为112*112,test的mode选择whole和slide是否有影响?哪个模式更适合小图?whole吗?

如果大小全部都是固定的112x112,用whole就好了

847001315 commented 2 years ago

昨天的config里好像没有加载预训练权重pretrained=None,不知道你后来有没有加上?

后面依旧没有加上,有一个疑惑,例如您刚刚给我发的config中的model的backbone的image_size为128,但预训练权重是224的,是否可以载入?我一开始感觉我的图像尺寸和model的backbone尺寸不同就没有加,后续可以去加一下。

可以载入的,finetune的分辨率可以和预训练不一致 这个模型比较大,医疗数据一般都比较少,如果不用预训练效果可能会比较差

好的!我后续去试验一下,刚刚开始接触mmseg框架,很多基础不清晰,非常打扰!!再一次感谢您!!想问一个问题,我的图片大小为112*112,test的mode选择whole和slide是否有影响?哪个模式更适合小图?whole吗?

如果大小全部都是固定的112x112,用whole就好了

好的!了解了!!!vitadaper好像接受不了图尺寸为112X112的,我之前单独抽取把vitadapter抽取出来,放入之前自己的模型中,会出现有一个层的特征图为3x3,另外一个本来应该和它同尺度的特征图为4x4(说的很不清晰,后面我把它全部向上取整后,就可以跑了)。是否我可以认为,最低尺寸应该应该为128x128?

czczup commented 2 years ago

昨天的config里好像没有加载预训练权重pretrained=None,不知道你后来有没有加上?

后面依旧没有加上,有一个疑惑,例如您刚刚给我发的config中的model的backbone的image_size为128,但预训练权重是224的,是否可以载入?我一开始感觉我的图像尺寸和model的backbone尺寸不同就没有加,后续可以去加一下。

可以载入的,finetune的分辨率可以和预训练不一致 这个模型比较大,医疗数据一般都比较少,如果不用预训练效果可能会比较差

好的!我后续去试验一下,刚刚开始接触mmseg框架,很多基础不清晰,非常打扰!!再一次感谢您!!想问一个问题,我的图片大小为112*112,test的mode选择whole和slide是否有影响?哪个模式更适合小图?whole吗?

如果大小全部都是固定的112x112,用whole就好了

好的!了解了!!!vitadaper好像接受不了图尺寸为112X112的,我之前单独抽取把vitadapter抽取出来,放入之前自己的模型中,会出现有一个层的特征图为3x3,另外一个本来应该和它同尺度的特征图为4x4(说的很不清晰,后面我把它全部向上取整后,就可以跑了)。是否我可以认为,最低尺寸应该应该为128x128?

确实。要求输入图像的分辨率能被32整除(因为最小的特征图是stride 32的),倒不一定是128x128

847001315 commented 2 years ago

昨天的config里好像没有加载预训练权重pretrained=None,不知道你后来有没有加上?

后面依旧没有加上,有一个疑惑,例如您刚刚给我发的config中的model的backbone的image_size为128,但预训练权重是224的,是否可以载入?我一开始感觉我的图像尺寸和model的backbone尺寸不同就没有加,后续可以去加一下。

可以载入的,finetune的分辨率可以和预训练不一致 这个模型比较大,医疗数据一般都比较少,如果不用预训练效果可能会比较差

好的!我后续去试验一下,刚刚开始接触mmseg框架,很多基础不清晰,非常打扰!!再一次感谢您!!想问一个问题,我的图片大小为112*112,test的mode选择whole和slide是否有影响?哪个模式更适合小图?whole吗?

如果大小全部都是固定的112x112,用whole就好了

好的!了解了!!!vitadaper好像接受不了图尺寸为112X112的,我之前单独抽取把vitadapter抽取出来,放入之前自己的模型中,会出现有一个层的特征图为3x3,另外一个本来应该和它同尺度的特征图为4x4(说的很不清晰,后面我把它全部向上取整后,就可以跑了)。是否我可以认为,最低尺寸应该应该为128x128?

确实。要求输入图像的分辨率能被32整除(因为最小的特征图是stride 32的),倒不一定是128x128

好的!!!非常感谢╰(´︶`)╯!!如果我对mmseg和vit-adapter更熟悉了之后,是否可以写一个博客用来介绍如何在本项目中自定义数据集?

czczup commented 2 years ago

昨天的config里好像没有加载预训练权重pretrained=None,不知道你后来有没有加上?

后面依旧没有加上,有一个疑惑,例如您刚刚给我发的config中的model的backbone的image_size为128,但预训练权重是224的,是否可以载入?我一开始感觉我的图像尺寸和model的backbone尺寸不同就没有加,后续可以去加一下。

可以载入的,finetune的分辨率可以和预训练不一致 这个模型比较大,医疗数据一般都比较少,如果不用预训练效果可能会比较差

好的!我后续去试验一下,刚刚开始接触mmseg框架,很多基础不清晰,非常打扰!!再一次感谢您!!想问一个问题,我的图片大小为112*112,test的mode选择whole和slide是否有影响?哪个模式更适合小图?whole吗?

如果大小全部都是固定的112x112,用whole就好了

好的!了解了!!!vitadaper好像接受不了图尺寸为112X112的,我之前单独抽取把vitadapter抽取出来,放入之前自己的模型中,会出现有一个层的特征图为3x3,另外一个本来应该和它同尺度的特征图为4x4(说的很不清晰,后面我把它全部向上取整后,就可以跑了)。是否我可以认为,最低尺寸应该应该为128x128?

确实。要求输入图像的分辨率能被32整除(因为最小的特征图是stride 32的),倒不一定是128x128

好的!!!非常感谢╰(´︶`)╯!!如果我对mmseg和vit-adapter更熟悉了之后,是否可以写一个博客用来介绍如何在本项目中自定义数据集?

当然可以😊

847001315 commented 2 years ago

您好~ 我这两天去把您之前说的发的config进行修改一些路径,已经可以跑了,并且得到了比deeplabv3_resnet50更好的效果。但是我在跑另外一个3类别数据集【如果加上背景是4类,但我并不打算计算背景】的时候,验证集的对于这三个类还能达到姣好的效果,但测试集得出来的结果仅有0和2两个像素值,没有1像素值,也没有其它像素值,目前我打算去将背景也加为一类,但是我有点困惑,如果说背景不加入其中的话,那确实分割出来只会有三个可能的像素值【但城市景观好像就没有背景类?】。所以想问:

  1. 如果我没将背景(像素值255)也算作一类,是否会影响分类结果?
  2. 测试集仅得出了0和2的像素值,并没有1的像素值,这可能存在什么原因? 以下是验证集得到的结果: O5D%ZFPS$R98PJ8LH08{7K0

我接下来会将背景类加入~ 非常感谢您!!

czczup commented 2 years ago

您好~ 我这两天去把您之前说的发的config进行修改一些路径,已经可以跑了,并且得到了比deeplabv3_resnet50更好的效果。但是我在跑另外一个3类别数据集【如果加上背景是4类,但我并不打算计算背景】的时候,验证集的对于这三个类还能达到姣好的效果,但测试集得出来的结果仅有0和2两个像素值,没有1像素值,也没有其它像素值,目前我打算去将背景也加为一类,但是我有点困惑,如果说背景不加入其中的话,那确实分割出来只会有三个可能的像素值【但城市景观好像就没有背景类?】。所以想问:

  1. 如果我没将背景(像素值255)也算作一类,是否会影响分类结果?
  2. 测试集仅得出了0和2的像素值,并没有1的像素值,这可能存在什么原因? 以下是验证集得到的结果: O5D%ZFPS$R98PJ8LH08{7K0

我接下来会将背景类加入~ 非常感谢您!!

  1. 背景不参与是可以的,不过通常像素值0是背景,而255是要忽略的像素
  2. 请问你的reduce_zero_label是设的什么
  3. 我有一个办法应该可以解决,就是重新映射一下标签,背景为0,其他的为1、2、3,reduce_zero_label=True
847001315 commented 2 years ago

您好~ 我这两天去把您之前说的发的config进行修改一些路径,已经可以跑了,并且得到了比deeplabv3_resnet50更好的效果。但是我在跑另外一个3类别数据集【如果加上背景是4类,但我并不打算计算背景】的时候,验证集的对于这三个类还能达到姣好的效果,但测试集得出来的结果仅有0和2两个像素值,没有1像素值,也没有其它像素值,目前我打算去将背景也加为一类,但是我有点困惑,如果说背景不加入其中的话,那确实分割出来只会有三个可能的像素值【但城市景观好像就没有背景类?】。所以想问:

  1. 如果我没将背景(像素值255)也算作一类,是否会影响分类结果?
  2. 测试集仅得出了0和2的像素值,并没有1的像素值,这可能存在什么原因? 以下是验证集得到的结果: O5D%ZFPS$R98PJ8LH08{7K0

我接下来会将背景类加入~ 非常感谢您!!

  1. 背景不参与是可以的,不过通常像素值0是背景,而255是要忽略的像素
  2. 请问你的reduce_zero_label是设的什么
  3. 我有一个办法应该可以解决,就是重新映射一下标签,背景为0,其他的为1、2、3,reduce_zero_label=True

好的,谢谢您! 我之前设置的reduce_zero_label=false,然后0 1 2 为具体的三个目标类,我手动将mask的背景设为255。请问mmseg默认255是不计算的吗? 对于第三点,我马上去尝试

JavaZeroo commented 1 year ago

昨天的config里好像没有加载预训练权重pretrained=None,不知道你后来有没有加上?

后面依旧没有加上,有一个疑惑,例如您刚刚给我发的config中的model的backbone的image_size为128,但预训练权重是224的,是否可以载入?我一开始感觉我的图像尺寸和model的backbone尺寸不同就没有加,后续可以去加一下。

可以载入的,finetune的分辨率可以和预训练不一致 这个模型比较大,医疗数据一般都比较少,如果不用预训练效果可能会比较差

好的!我后续去试验一下,刚刚开始接触mmseg框架,很多基础不清晰,非常打扰!!再一次感谢您!!想问一个问题,我的图片大小为112*112,test的mode选择whole和slide是否有影响?哪个模式更适合小图?whole吗?

如果大小全部都是固定的112x112,用whole就好了

好的!了解了!!!vitadaper好像接受不了图尺寸为112X112的,我之前单独抽取把vitadapter抽取出来,放入之前自己的模型中,会出现有一个层的特征图为3x3,另外一个本来应该和它同尺度的特征图为4x4(说的很不清晰,后面我把它全部向上取整后,就可以跑了)。是否我可以认为,最低尺寸应该应该为128x128?

确实。要求输入图像的分辨率能被32整除(因为最小的特征图是stride 32的),倒不一定是128x128

好的!!!非常感谢╰(´︶`)╯!!如果我对mmseg和vit-adapter更熟悉了之后,是否可以写一个博客用来介绍如何在本项目中自定义数据集?

哥们,博客写好了吗😁