File size: 2,512 Bytes
938e515 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 |
# Copyright (c) Facebook, Inc. and its affiliates.
from abc import ABCMeta, abstractmethod
from typing import Dict
import torch.nn as nn
from detectron2.layers import ShapeSpec
__all__ = ["Backbone"]
class Backbone(nn.Module, metaclass=ABCMeta):
"""
Abstract base class for network backbones.
"""
def __init__(self):
"""
The `__init__` method of any subclass can specify its own set of arguments.
"""
super().__init__()
@abstractmethod
def forward(self):
"""
Subclasses must override this method, but adhere to the same return type.
Returns:
dict[str->Tensor]: mapping from feature name (e.g., "res2") to tensor
"""
pass
@property
def size_divisibility(self) -> int:
"""
Some backbones require the input height and width to be divisible by a
specific integer. This is typically true for encoder / decoder type networks
with lateral connection (e.g., FPN) for which feature maps need to match
dimension in the "bottom up" and "top down" paths. Set to 0 if no specific
input size divisibility is required.
"""
return 0
@property
def padding_constraints(self) -> Dict[str, int]:
"""
This property is a generalization of size_divisibility. Some backbones and training
recipes require specific padding constraints, such as enforcing divisibility by a specific
integer (e.g., FPN) or padding to a square (e.g., ViTDet with large-scale jitter
in :paper:vitdet). `padding_constraints` contains these optional items like:
{
"size_divisibility": int,
"square_size": int,
# Future options are possible
}
`size_divisibility` will read from here if presented and `square_size` indicates the
square padding size if `square_size` > 0.
TODO: use type of Dict[str, int] to avoid torchscipt issues. The type of padding_constraints
could be generalized as TypedDict (Python 3.8+) to support more types in the future.
"""
return {}
def output_shape(self):
"""
Returns:
dict[str->ShapeSpec]
"""
# this is a backward-compatible default
return {
name: ShapeSpec(
channels=self._out_feature_channels[name], stride=self._out_feature_strides[name]
)
for name in self._out_features
}
|