Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
s920243400
PaddleDetection
提交
f4a3856f
P
PaddleDetection
项目概览
s920243400
/
PaddleDetection
与 Fork 源项目一致
Fork自
PaddlePaddle / PaddleDetection
通知
2
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
P
PaddleDetection
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
提交
f4a3856f
编写于
9月 18, 2020
作者:
W
wubinghong
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Refine the bifpn for efficientnet-d0
上级
946094e3
变更
3
显示空白变更内容
内联
并排
Showing
3 changed file
with
41 addition
and
105 deletion
+41
-105
ppdet/modeling/architectures/efficientdet.py
ppdet/modeling/architectures/efficientdet.py
+1
-1
ppdet/modeling/backbones/bifpn.py
ppdet/modeling/backbones/bifpn.py
+7
-11
ppdet/modeling/backbones/efficientnet.py
ppdet/modeling/backbones/efficientnet.py
+33
-93
未找到文件。
ppdet/modeling/architectures/efficientdet.py
浏览文件 @
f4a3856f
...
...
@@ -64,7 +64,7 @@ class EfficientDet(object):
mixed_precision_enabled
=
mixed_precision_global_state
()
is
not
None
if
mixed_precision_enabled
:
im
=
fluid
.
layers
.
cast
(
im
,
'float16'
)
body_feats
=
self
.
backbone
(
im
,
mode
)
body_feats
=
self
.
backbone
(
im
)
if
mixed_precision_enabled
:
body_feats
=
[
fluid
.
layers
.
cast
(
f
,
'float32'
)
for
f
in
body_feats
]
body_feats
=
self
.
fpn
(
body_feats
)
...
...
ppdet/modeling/backbones/bifpn.py
浏览文件 @
f4a3856f
...
...
@@ -83,9 +83,7 @@ class BiFPNCell(object):
default_initializer
=
fluid
.
initializer
.
Constant
(
1.
))
self
.
eps
=
1e-4
def
__call__
(
self
,
inputs
,
cell_name
=
''
,
is_first_time
=
False
,
p4_2_p5_2
=
[]):
assert
len
(
inputs
)
==
self
.
levels
assert
((
is_first_time
)
and
(
len
(
p4_2_p5_2
)
!=
0
))
or
((
not
is_first_time
)
and
(
len
(
p4_2_p5_2
)
==
0
))
def
__call__
(
self
,
inputs
,
cell_name
=
''
):
def
upsample
(
feat
):
return
fluid
.
layers
.
resize_nearest
(
feat
,
scale
=
2.
)
...
...
@@ -108,7 +106,8 @@ class BiFPNCell(object):
bigates
/=
fluid
.
layers
.
reduce_sum
(
bigates
,
dim
=
1
,
keep_dim
=
True
)
+
self
.
eps
feature_maps
=
list
(
inputs
)
# make a copy # top down path
# top down path
feature_maps
=
list
(
inputs
[:
self
.
levels
])
# make a copy
for
l
in
range
(
self
.
levels
-
1
):
p
=
self
.
levels
-
l
-
2
w1
=
fluid
.
layers
.
slice
(
...
...
@@ -133,7 +132,8 @@ class BiFPNCell(object):
feature_maps
[
p
]
=
fuse_conv
(
w1
*
below
+
w2
*
inputs
[
p
],
name
=
name
)
else
:
if
is_first_time
:
# For the first loop in BiFPN
if
len
(
inputs
)
!=
self
.
levels
:
if
p
<
self
.
inputs_layer_num
:
w1
=
fluid
.
layers
.
slice
(
trigates
,
axes
=
[
0
,
1
],
starts
=
[
p
-
1
,
0
],
ends
=
[
p
,
1
])
...
...
@@ -141,7 +141,7 @@ class BiFPNCell(object):
trigates
,
axes
=
[
0
,
1
],
starts
=
[
p
-
1
,
1
],
ends
=
[
p
,
2
])
w3
=
fluid
.
layers
.
slice
(
trigates
,
axes
=
[
0
,
1
],
starts
=
[
p
-
1
,
2
],
ends
=
[
p
,
3
])
feature_maps
[
p
]
=
fuse_conv
(
w1
*
feature_maps
[
p
]
+
w2
*
below
+
w3
*
p4_2_p5_2
[
p
-
1
],
name
=
name
)
w1
*
feature_maps
[
p
]
+
w2
*
below
+
w3
*
inputs
[
p
-
1
+
self
.
levels
],
name
=
name
)
else
:
# For P6"
w1
=
fluid
.
layers
.
slice
(
trigates
,
axes
=
[
0
,
1
],
starts
=
[
p
-
1
,
0
],
ends
=
[
p
,
1
])
...
...
@@ -233,7 +233,6 @@ class BiFPN(object):
name
=
'resample_downsample_{}'
.
format
(
idx
))
feats
.
append
(
feat
)
# Handle the p4_2 and p5_2 with another 1x1 conv & bn layer
p4_2_p5_2
=
[]
for
idx
in
range
(
1
,
len
(
inputs
)):
feat
=
fluid
.
layers
.
conv2d
(
inputs
[
idx
],
...
...
@@ -250,13 +249,10 @@ class BiFPN(object):
param_attr
=
ParamAttr
(
initializer
=
Constant
(
1.0
),
regularizer
=
L2Decay
(
0.
)),
bias_attr
=
ParamAttr
(
regularizer
=
L2Decay
(
0.
)),
name
=
'resample2_bn_{}'
.
format
(
idx
))
p4_2_p5_2
.
append
(
feat
)
feats
.
append
(
feat
)
biFPN
=
BiFPNCell
(
self
.
num_chan
,
self
.
levels
,
len
(
inputs
))
for
r
in
range
(
self
.
repeat
):
if
r
==
0
:
feats
=
biFPN
(
feats
,
cell_name
=
'bifpn_{}'
.
format
(
r
),
is_first_time
=
True
,
p4_2_p5_2
=
p4_2_p5_2
)
else
:
feats
=
biFPN
(
feats
,
cell_name
=
'bifpn_{}'
.
format
(
r
))
return
feats
ppdet/modeling/backbones/efficientnet.py
浏览文件 @
f4a3856f
...
...
@@ -28,15 +28,12 @@ __all__ = ['EfficientNet']
GlobalParams
=
collections
.
namedtuple
(
'GlobalParams'
,
[
'batch_norm_momentum'
,
'batch_norm_epsilon'
,
'width_coefficient'
,
'depth_coefficient'
,
'depth_divisor'
,
'min_depth'
,
'drop_connect_rate'
,
'relu_fn'
,
'batch_norm'
,
'use_se'
,
'local_pooling'
,
'condconv_num_experts'
,
'clip_projection_output'
,
'blocks_args'
,
'fix_head_stem'
'depth_coefficient'
,
'depth_divisor'
])
BlockArgs
=
collections
.
namedtuple
(
'BlockArgs'
,
[
'kernel_size'
,
'num_repeat'
,
'input_filters'
,
'output_filters'
,
'expand_ratio'
,
'id_skip'
,
'stride'
,
'se_ratio'
,
'conv_type'
,
'fused_conv'
,
'super_pixel'
,
'condconv'
'expand_ratio'
,
'stride'
,
'se_ratio'
])
GlobalParams
.
__new__
.
__defaults__
=
(
None
,
)
*
len
(
GlobalParams
.
_fields
)
...
...
@@ -63,13 +60,8 @@ def _decode_block_string(block_string):
input_filters
=
int
(
options
[
'i'
]),
output_filters
=
int
(
options
[
'o'
]),
expand_ratio
=
int
(
options
[
'e'
]),
id_skip
=
(
'noskip'
not
in
block_string
),
se_ratio
=
float
(
options
[
'se'
])
if
'se'
in
options
else
None
,
stride
=
int
(
options
[
's'
][
0
]),
conv_type
=
int
(
options
[
'c'
])
if
'c'
in
options
else
0
,
fused_conv
=
int
(
options
[
'f'
])
if
'f'
in
options
else
0
,
super_pixel
=
int
(
options
[
'p'
])
if
'p'
in
options
else
0
,
condconv
=
(
'cc'
in
block_string
))
stride
=
int
(
options
[
's'
][
0
]))
def
get_model_params
(
scale
):
...
...
@@ -96,34 +88,27 @@ def get_model_params(scale):
'b5'
:
(
1.6
,
2.2
),
'b6'
:
(
1.8
,
2.6
),
'b7'
:
(
2.0
,
3.1
),
'l2'
:
(
4.3
,
5.3
),
}
w
,
d
=
params_dict
[
scale
]
global_params
=
GlobalParams
(
blocks_args
=
block_strings
,
batch_norm_momentum
=
0.99
,
batch_norm_epsilon
=
1e-3
,
drop_connect_rate
=
0
if
scale
==
'b0'
else
0.2
,
width_coefficient
=
w
,
depth_coefficient
=
d
,
depth_divisor
=
8
,
min_depth
=
None
,
fix_head_stem
=
False
,
use_se
=
True
,
clip_projection_output
=
False
)
depth_divisor
=
8
)
return
block_args
,
global_params
def
round_filters
(
filters
,
global_params
,
skip
=
False
):
def
round_filters
(
filters
,
global_params
):
multiplier
=
global_params
.
width_coefficient
if
skip
or
not
multiplier
:
if
not
multiplier
:
return
filters
divisor
=
global_params
.
depth_divisor
filters
*=
multiplier
min_depth
=
global_params
.
min_depth
or
divisor
min_depth
=
divisor
new_filters
=
max
(
min_depth
,
int
(
filters
+
divisor
/
2
)
//
divisor
*
divisor
)
if
new_filters
<
0.9
*
filters
:
# prevent rounding by more than 10%
...
...
@@ -131,9 +116,9 @@ def round_filters(filters, global_params, skip=False):
return
int
(
new_filters
)
def
round_repeats
(
repeats
,
global_params
,
skip
=
False
):
def
round_repeats
(
repeats
,
global_params
):
multiplier
=
global_params
.
depth_coefficient
if
skip
or
not
multiplier
:
if
not
multiplier
:
return
repeats
return
int
(
math
.
ceil
(
multiplier
*
repeats
))
...
...
@@ -178,28 +163,14 @@ def batch_norm(inputs, momentum, eps, name=None):
bias_attr
=
bias_attr
)
def
_drop_connect
(
inputs
,
prob
,
mode
):
if
mode
!=
'train'
:
return
inputs
keep_prob
=
1.0
-
prob
inputs_shape
=
fluid
.
layers
.
shape
(
inputs
)
random_tensor
=
keep_prob
+
fluid
.
layers
.
uniform_random
(
shape
=
[
inputs_shape
[
0
],
1
,
1
,
1
],
min
=
0.
,
max
=
1.
)
binary_tensor
=
fluid
.
layers
.
floor
(
random_tensor
)
output
=
inputs
/
keep_prob
*
binary_tensor
return
output
def
mb_conv_block
(
inputs
,
input_filters
,
output_filters
,
expand_ratio
,
kernel_size
,
stride
,
id_skip
,
drop_connect_rate
,
momentum
,
eps
,
mode
,
se_ratio
=
None
,
name
=
None
):
feats
=
inputs
...
...
@@ -238,9 +209,7 @@ def mb_conv_block(inputs,
feats
=
conv2d
(
feats
,
output_filters
,
1
,
name
=
name
+
'_project_conv'
)
feats
=
batch_norm
(
feats
,
momentum
,
eps
,
name
=
name
+
'_bn2'
)
if
id_skip
and
stride
==
1
and
input_filters
==
output_filters
:
if
drop_connect_rate
:
feats
=
_drop_connect
(
feats
,
drop_connect_rate
,
mode
)
if
stride
==
1
and
input_filters
==
output_filters
:
feats
=
fluid
.
layers
.
elementwise_add
(
feats
,
inputs
)
return
feats
...
...
@@ -269,14 +238,12 @@ class EfficientNet(object):
self
.
scale
=
scale
self
.
use_se
=
use_se
def
__call__
(
self
,
inputs
,
mode
):
assert
mode
in
[
'train'
,
'test'
],
\
"only 'train' and 'test' mode are supported"
def
__call__
(
self
,
inputs
):
blocks_args
,
global_params
=
get_model_params
(
self
.
scale
)
momentum
=
global_params
.
batch_norm_momentum
eps
=
global_params
.
batch_norm_epsilon
num_filters
=
round_filters
(
blocks_args
[
0
].
input_filters
,
global_params
,
global_params
.
fix_head_stem
)
num_filters
=
round_filters
(
32
,
global_params
)
feats
=
conv2d
(
inputs
,
num_filters
=
num_filters
,
...
...
@@ -287,61 +254,34 @@ class EfficientNet(object):
feats
=
fluid
.
layers
.
swish
(
feats
)
layer_count
=
0
num_blocks
=
sum
([
block_arg
.
num_repeat
for
block_arg
in
blocks_args
])
feature_maps
=
[]
for
block_arg
in
blocks_args
:
# Update block input and output filters based on depth multiplier.
block_arg
=
block_arg
.
_replace
(
input_filters
=
round_filters
(
block_arg
.
input_filters
,
global_params
),
output_filters
=
round_filters
(
block_arg
.
output_filters
,
global_params
),
num_repeat
=
round_repeats
(
block_arg
.
num_repeat
,
global_params
))
# The first block needs to take care of stride,
# and filter size increase.
drop_connect_rate
=
global_params
.
drop_connect_rate
if
drop_connect_rate
:
drop_connect_rate
*=
float
(
layer_count
)
/
num_blocks
feats
=
mb_conv_block
(
feats
,
block_arg
.
input_filters
,
block_arg
.
output_filters
,
block_arg
.
expand_ratio
,
block_arg
.
kernel_size
,
block_arg
.
stride
,
block_arg
.
id_skip
,
drop_connect_rate
,
momentum
,
eps
,
mode
,
se_ratio
=
block_arg
.
se_ratio
,
name
=
'_blocks.{}.'
.
format
(
layer_count
))
layer_count
+=
1
# Other block
if
block_arg
.
num_repeat
>
1
:
block_arg
=
block_arg
.
_replace
(
input_filters
=
block_arg
.
output_filters
,
stride
=
1
)
for
b
,
block_arg
in
enumerate
(
blocks_args
):
for
r
in
range
(
block_arg
.
num_repeat
):
input_filters
=
round_filters
(
block_arg
.
input_filters
,
global_params
)
output_filters
=
round_filters
(
block_arg
.
output_filters
,
global_params
)
kernel_size
=
block_arg
.
kernel_size
stride
=
block_arg
.
stride
se_ratio
=
None
if
self
.
use_se
:
se_ratio
=
block_arg
.
se_ratio
if
r
>
0
:
input_filters
=
output_filters
stride
=
1
for
_
in
range
(
block_arg
.
num_repeat
-
1
):
drop_connect_rate
=
global_params
.
drop_connect_rate
if
drop_connect_rate
:
drop_connect_rate
*=
float
(
layer_count
)
/
num_blocks
feats
=
mb_conv_block
(
feats
,
block_arg
.
input_filters
,
block_arg
.
output_filters
,
input_filters
,
output_filters
,
block_arg
.
expand_ratio
,
block_arg
.
kernel_size
,
block_arg
.
stride
,
block_arg
.
id_skip
,
drop_connect_rate
,
kernel_size
,
stride
,
momentum
,
eps
,
mode
,
se_ratio
=
block_arg
.
se_ratio
,
se_ratio
=
se_ratio
,
name
=
'_blocks.{}.'
.
format
(
layer_count
))
layer_count
+=
1
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录