keras-hub-nightly 0.15.0.dev20240823171555__py3-none-any.whl → 0.16.0.dev2024092017__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (198) hide show
  1. keras_hub/__init__.py +0 -6
  2. keras_hub/api/__init__.py +2 -0
  3. keras_hub/api/bounding_box/__init__.py +36 -0
  4. keras_hub/api/layers/__init__.py +14 -0
  5. keras_hub/api/models/__init__.py +97 -48
  6. keras_hub/api/tokenizers/__init__.py +30 -0
  7. keras_hub/api/utils/__init__.py +22 -0
  8. keras_hub/src/api_export.py +15 -9
  9. keras_hub/src/bounding_box/__init__.py +13 -0
  10. keras_hub/src/bounding_box/converters.py +529 -0
  11. keras_hub/src/bounding_box/formats.py +162 -0
  12. keras_hub/src/bounding_box/iou.py +263 -0
  13. keras_hub/src/bounding_box/to_dense.py +95 -0
  14. keras_hub/src/bounding_box/to_ragged.py +99 -0
  15. keras_hub/src/bounding_box/utils.py +194 -0
  16. keras_hub/src/bounding_box/validate_format.py +99 -0
  17. keras_hub/src/layers/preprocessing/audio_converter.py +121 -0
  18. keras_hub/src/layers/preprocessing/image_converter.py +130 -0
  19. keras_hub/src/layers/preprocessing/masked_lm_mask_generator.py +2 -0
  20. keras_hub/src/layers/preprocessing/multi_segment_packer.py +9 -8
  21. keras_hub/src/layers/preprocessing/preprocessing_layer.py +2 -29
  22. keras_hub/src/layers/preprocessing/random_deletion.py +33 -31
  23. keras_hub/src/layers/preprocessing/random_swap.py +33 -31
  24. keras_hub/src/layers/preprocessing/resizing_image_converter.py +101 -0
  25. keras_hub/src/layers/preprocessing/start_end_packer.py +3 -2
  26. keras_hub/src/models/albert/__init__.py +1 -2
  27. keras_hub/src/models/albert/albert_masked_lm_preprocessor.py +6 -86
  28. keras_hub/src/models/albert/{albert_classifier.py → albert_text_classifier.py} +34 -10
  29. keras_hub/src/models/albert/{albert_preprocessor.py → albert_text_classifier_preprocessor.py} +14 -70
  30. keras_hub/src/models/albert/albert_tokenizer.py +17 -36
  31. keras_hub/src/models/backbone.py +12 -34
  32. keras_hub/src/models/bart/__init__.py +1 -2
  33. keras_hub/src/models/bart/bart_seq_2_seq_lm_preprocessor.py +21 -148
  34. keras_hub/src/models/bart/bart_tokenizer.py +12 -39
  35. keras_hub/src/models/bert/__init__.py +1 -5
  36. keras_hub/src/models/bert/bert_masked_lm_preprocessor.py +6 -87
  37. keras_hub/src/models/bert/bert_presets.py +1 -4
  38. keras_hub/src/models/bert/{bert_classifier.py → bert_text_classifier.py} +19 -12
  39. keras_hub/src/models/bert/{bert_preprocessor.py → bert_text_classifier_preprocessor.py} +14 -70
  40. keras_hub/src/models/bert/bert_tokenizer.py +17 -35
  41. keras_hub/src/models/bloom/__init__.py +1 -2
  42. keras_hub/src/models/bloom/bloom_causal_lm_preprocessor.py +6 -91
  43. keras_hub/src/models/bloom/bloom_tokenizer.py +12 -41
  44. keras_hub/src/models/causal_lm.py +10 -29
  45. keras_hub/src/models/causal_lm_preprocessor.py +195 -0
  46. keras_hub/src/models/csp_darknet/csp_darknet_backbone.py +54 -15
  47. keras_hub/src/models/deberta_v3/__init__.py +1 -4
  48. keras_hub/src/models/deberta_v3/deberta_v3_masked_lm_preprocessor.py +14 -77
  49. keras_hub/src/models/deberta_v3/{deberta_v3_classifier.py → deberta_v3_text_classifier.py} +16 -11
  50. keras_hub/src/models/deberta_v3/{deberta_v3_preprocessor.py → deberta_v3_text_classifier_preprocessor.py} +23 -64
  51. keras_hub/src/models/deberta_v3/deberta_v3_tokenizer.py +30 -25
  52. keras_hub/src/models/densenet/densenet_backbone.py +46 -22
  53. keras_hub/src/models/distil_bert/__init__.py +1 -4
  54. keras_hub/src/models/distil_bert/distil_bert_masked_lm_preprocessor.py +14 -76
  55. keras_hub/src/models/distil_bert/{distil_bert_classifier.py → distil_bert_text_classifier.py} +17 -12
  56. keras_hub/src/models/distil_bert/{distil_bert_preprocessor.py → distil_bert_text_classifier_preprocessor.py} +23 -63
  57. keras_hub/src/models/distil_bert/distil_bert_tokenizer.py +19 -35
  58. keras_hub/src/models/efficientnet/__init__.py +13 -0
  59. keras_hub/src/models/efficientnet/efficientnet_backbone.py +569 -0
  60. keras_hub/src/models/efficientnet/fusedmbconv.py +229 -0
  61. keras_hub/src/models/efficientnet/mbconv.py +238 -0
  62. keras_hub/src/models/electra/__init__.py +1 -2
  63. keras_hub/src/models/electra/electra_tokenizer.py +17 -32
  64. keras_hub/src/models/f_net/__init__.py +1 -2
  65. keras_hub/src/models/f_net/f_net_masked_lm_preprocessor.py +12 -78
  66. keras_hub/src/models/f_net/{f_net_classifier.py → f_net_text_classifier.py} +17 -10
  67. keras_hub/src/models/f_net/{f_net_preprocessor.py → f_net_text_classifier_preprocessor.py} +19 -63
  68. keras_hub/src/models/f_net/f_net_tokenizer.py +17 -35
  69. keras_hub/src/models/falcon/__init__.py +1 -2
  70. keras_hub/src/models/falcon/falcon_causal_lm_preprocessor.py +6 -89
  71. keras_hub/src/models/falcon/falcon_tokenizer.py +12 -35
  72. keras_hub/src/models/gemma/__init__.py +1 -2
  73. keras_hub/src/models/gemma/gemma_causal_lm_preprocessor.py +6 -90
  74. keras_hub/src/models/gemma/gemma_decoder_block.py +1 -1
  75. keras_hub/src/models/gemma/gemma_tokenizer.py +12 -23
  76. keras_hub/src/models/gpt2/__init__.py +1 -2
  77. keras_hub/src/models/gpt2/gpt2_causal_lm_preprocessor.py +6 -89
  78. keras_hub/src/models/gpt2/gpt2_preprocessor.py +12 -90
  79. keras_hub/src/models/gpt2/gpt2_tokenizer.py +12 -34
  80. keras_hub/src/models/gpt_neo_x/gpt_neo_x_causal_lm_preprocessor.py +6 -91
  81. keras_hub/src/models/gpt_neo_x/gpt_neo_x_tokenizer.py +12 -34
  82. keras_hub/src/models/image_classifier.py +0 -5
  83. keras_hub/src/models/image_classifier_preprocessor.py +83 -0
  84. keras_hub/src/models/llama/__init__.py +1 -2
  85. keras_hub/src/models/llama/llama_causal_lm_preprocessor.py +6 -85
  86. keras_hub/src/models/llama/llama_tokenizer.py +12 -25
  87. keras_hub/src/models/llama3/__init__.py +1 -2
  88. keras_hub/src/models/llama3/llama3_causal_lm_preprocessor.py +6 -89
  89. keras_hub/src/models/llama3/llama3_tokenizer.py +12 -33
  90. keras_hub/src/models/masked_lm.py +0 -2
  91. keras_hub/src/models/masked_lm_preprocessor.py +156 -0
  92. keras_hub/src/models/mistral/__init__.py +1 -2
  93. keras_hub/src/models/mistral/mistral_causal_lm_preprocessor.py +6 -91
  94. keras_hub/src/models/mistral/mistral_tokenizer.py +12 -23
  95. keras_hub/src/models/mix_transformer/mix_transformer_backbone.py +2 -2
  96. keras_hub/src/models/mobilenet/__init__.py +13 -0
  97. keras_hub/src/models/mobilenet/mobilenet_backbone.py +530 -0
  98. keras_hub/src/models/mobilenet/mobilenet_image_classifier.py +114 -0
  99. keras_hub/src/models/opt/__init__.py +1 -2
  100. keras_hub/src/models/opt/opt_causal_lm_preprocessor.py +6 -93
  101. keras_hub/src/models/opt/opt_tokenizer.py +12 -41
  102. keras_hub/src/models/pali_gemma/__init__.py +1 -4
  103. keras_hub/src/models/pali_gemma/pali_gemma_causal_lm_preprocessor.py +28 -28
  104. keras_hub/src/models/pali_gemma/pali_gemma_image_converter.py +25 -0
  105. keras_hub/src/models/pali_gemma/pali_gemma_presets.py +5 -5
  106. keras_hub/src/models/pali_gemma/pali_gemma_tokenizer.py +11 -3
  107. keras_hub/src/models/phi3/__init__.py +1 -2
  108. keras_hub/src/models/phi3/phi3_causal_lm.py +3 -9
  109. keras_hub/src/models/phi3/phi3_causal_lm_preprocessor.py +6 -89
  110. keras_hub/src/models/phi3/phi3_tokenizer.py +12 -36
  111. keras_hub/src/models/preprocessor.py +72 -83
  112. keras_hub/src/models/resnet/__init__.py +6 -0
  113. keras_hub/src/models/resnet/resnet_backbone.py +390 -42
  114. keras_hub/src/models/resnet/resnet_image_classifier.py +33 -6
  115. keras_hub/src/models/resnet/resnet_image_classifier_preprocessor.py +28 -0
  116. keras_hub/src/models/{llama3/llama3_preprocessor.py → resnet/resnet_image_converter.py} +7 -5
  117. keras_hub/src/models/resnet/resnet_presets.py +95 -0
  118. keras_hub/src/models/retinanet/__init__.py +13 -0
  119. keras_hub/src/models/retinanet/anchor_generator.py +175 -0
  120. keras_hub/src/models/retinanet/box_matcher.py +259 -0
  121. keras_hub/src/models/retinanet/non_max_supression.py +578 -0
  122. keras_hub/src/models/roberta/__init__.py +1 -2
  123. keras_hub/src/models/roberta/roberta_masked_lm_preprocessor.py +22 -74
  124. keras_hub/src/models/roberta/{roberta_classifier.py → roberta_text_classifier.py} +16 -11
  125. keras_hub/src/models/roberta/{roberta_preprocessor.py → roberta_text_classifier_preprocessor.py} +21 -53
  126. keras_hub/src/models/roberta/roberta_tokenizer.py +13 -52
  127. keras_hub/src/models/seq_2_seq_lm_preprocessor.py +269 -0
  128. keras_hub/src/models/stable_diffusion_v3/__init__.py +13 -0
  129. keras_hub/src/models/stable_diffusion_v3/clip_encoder_block.py +103 -0
  130. keras_hub/src/models/stable_diffusion_v3/clip_preprocessor.py +93 -0
  131. keras_hub/src/models/stable_diffusion_v3/clip_text_encoder.py +149 -0
  132. keras_hub/src/models/stable_diffusion_v3/clip_tokenizer.py +167 -0
  133. keras_hub/src/models/stable_diffusion_v3/mmdit.py +427 -0
  134. keras_hub/src/models/stable_diffusion_v3/mmdit_block.py +317 -0
  135. keras_hub/src/models/stable_diffusion_v3/t5_xxl_preprocessor.py +74 -0
  136. keras_hub/src/models/stable_diffusion_v3/t5_xxl_text_encoder.py +155 -0
  137. keras_hub/src/models/stable_diffusion_v3/vae_attention.py +126 -0
  138. keras_hub/src/models/stable_diffusion_v3/vae_image_decoder.py +186 -0
  139. keras_hub/src/models/t5/__init__.py +1 -2
  140. keras_hub/src/models/t5/t5_tokenizer.py +13 -23
  141. keras_hub/src/models/task.py +71 -116
  142. keras_hub/src/models/{classifier.py → text_classifier.py} +19 -13
  143. keras_hub/src/models/text_classifier_preprocessor.py +138 -0
  144. keras_hub/src/models/whisper/__init__.py +1 -2
  145. keras_hub/src/models/whisper/{whisper_audio_feature_extractor.py → whisper_audio_converter.py} +20 -18
  146. keras_hub/src/models/whisper/whisper_backbone.py +0 -3
  147. keras_hub/src/models/whisper/whisper_presets.py +10 -10
  148. keras_hub/src/models/whisper/whisper_tokenizer.py +20 -16
  149. keras_hub/src/models/xlm_roberta/__init__.py +1 -4
  150. keras_hub/src/models/xlm_roberta/xlm_roberta_masked_lm_preprocessor.py +26 -72
  151. keras_hub/src/models/xlm_roberta/{xlm_roberta_classifier.py → xlm_roberta_text_classifier.py} +16 -11
  152. keras_hub/src/models/xlm_roberta/{xlm_roberta_preprocessor.py → xlm_roberta_text_classifier_preprocessor.py} +26 -53
  153. keras_hub/src/models/xlm_roberta/xlm_roberta_tokenizer.py +25 -10
  154. keras_hub/src/tests/test_case.py +46 -0
  155. keras_hub/src/tokenizers/byte_pair_tokenizer.py +30 -17
  156. keras_hub/src/tokenizers/byte_tokenizer.py +14 -15
  157. keras_hub/src/tokenizers/sentence_piece_tokenizer.py +20 -7
  158. keras_hub/src/tokenizers/tokenizer.py +67 -32
  159. keras_hub/src/tokenizers/unicode_codepoint_tokenizer.py +14 -15
  160. keras_hub/src/tokenizers/word_piece_tokenizer.py +34 -47
  161. keras_hub/src/utils/imagenet/__init__.py +13 -0
  162. keras_hub/src/utils/imagenet/imagenet_utils.py +1067 -0
  163. keras_hub/src/utils/keras_utils.py +0 -50
  164. keras_hub/src/utils/preset_utils.py +230 -68
  165. keras_hub/src/utils/tensor_utils.py +187 -69
  166. keras_hub/src/utils/timm/convert_resnet.py +19 -16
  167. keras_hub/src/utils/timm/preset_loader.py +66 -0
  168. keras_hub/src/utils/transformers/convert_albert.py +193 -0
  169. keras_hub/src/utils/transformers/convert_bart.py +373 -0
  170. keras_hub/src/utils/transformers/convert_bert.py +7 -17
  171. keras_hub/src/utils/transformers/convert_distilbert.py +10 -20
  172. keras_hub/src/utils/transformers/convert_gemma.py +5 -19
  173. keras_hub/src/utils/transformers/convert_gpt2.py +5 -18
  174. keras_hub/src/utils/transformers/convert_llama3.py +7 -18
  175. keras_hub/src/utils/transformers/convert_mistral.py +129 -0
  176. keras_hub/src/utils/transformers/convert_pali_gemma.py +7 -29
  177. keras_hub/src/utils/transformers/preset_loader.py +77 -0
  178. keras_hub/src/utils/transformers/safetensor_utils.py +2 -2
  179. keras_hub/src/version_utils.py +1 -1
  180. keras_hub_nightly-0.16.0.dev2024092017.dist-info/METADATA +202 -0
  181. keras_hub_nightly-0.16.0.dev2024092017.dist-info/RECORD +334 -0
  182. {keras_hub_nightly-0.15.0.dev20240823171555.dist-info → keras_hub_nightly-0.16.0.dev2024092017.dist-info}/WHEEL +1 -1
  183. keras_hub/src/models/bart/bart_preprocessor.py +0 -276
  184. keras_hub/src/models/bloom/bloom_preprocessor.py +0 -185
  185. keras_hub/src/models/electra/electra_preprocessor.py +0 -154
  186. keras_hub/src/models/falcon/falcon_preprocessor.py +0 -187
  187. keras_hub/src/models/gemma/gemma_preprocessor.py +0 -191
  188. keras_hub/src/models/gpt_neo_x/gpt_neo_x_preprocessor.py +0 -145
  189. keras_hub/src/models/llama/llama_preprocessor.py +0 -189
  190. keras_hub/src/models/mistral/mistral_preprocessor.py +0 -190
  191. keras_hub/src/models/opt/opt_preprocessor.py +0 -188
  192. keras_hub/src/models/phi3/phi3_preprocessor.py +0 -190
  193. keras_hub/src/models/whisper/whisper_preprocessor.py +0 -326
  194. keras_hub/src/utils/timm/convert.py +0 -37
  195. keras_hub/src/utils/transformers/convert.py +0 -101
  196. keras_hub_nightly-0.15.0.dev20240823171555.dist-info/METADATA +0 -34
  197. keras_hub_nightly-0.15.0.dev20240823171555.dist-info/RECORD +0 -297
  198. {keras_hub_nightly-0.15.0.dev20240823171555.dist-info → keras_hub_nightly-0.16.0.dev2024092017.dist-info}/top_level.txt +0 -0
@@ -0,0 +1,569 @@
1
+ # Copyright 2024 The KerasHub Authors
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # https://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+ import math
15
+
16
+ import keras
17
+
18
+ from keras_hub.src.api_export import keras_hub_export
19
+ from keras_hub.src.models.efficientnet.fusedmbconv import FusedMBConvBlock
20
+ from keras_hub.src.models.efficientnet.mbconv import MBConvBlock
21
+ from keras_hub.src.models.feature_pyramid_backbone import FeaturePyramidBackbone
22
+
23
+
24
+ @keras_hub_export("keras_hub.models.EfficientNetBackbone")
25
+ class EfficientNetBackbone(FeaturePyramidBackbone):
26
+ """An EfficientNet backbone model.
27
+
28
+ This class encapsulates the architectures for both EfficientNetV1 and
29
+ EfficientNetV2. EfficientNetV2 uses Fused-MBConv Blocks and Neural
30
+ Architecture Search (NAS) to make models sizes much smaller while still
31
+ improving overall model quality.
32
+
33
+ References:
34
+ - [EfficientNet: Rethinking Model Scaling for Convolutional Neural Networks]
35
+ (https://arxiv.org/abs/1905.11946) (ICML 2019)
36
+ - [Based on the original keras.applications EfficientNet]
37
+ (https://github.com/keras-team/keras/blob/master/keras/applications/efficientnet.py)
38
+ - [EfficientNetV2: Smaller Models and Faster Training]
39
+ (https://arxiv.org/abs/2104.00298) (ICML 2021)
40
+
41
+ Args:
42
+ width_coefficient: float, scaling coefficient for network width.
43
+ depth_coefficient: float, scaling coefficient for network depth.
44
+ dropout: float, dropout rate at skip connections. The default
45
+ value is set to 0.2.
46
+ depth_divisor: integer, a unit of network width. The default value is
47
+ set to 8.
48
+ activation: activation function to use between each convolutional layer.
49
+ input_shape: optional shape tuple, it should have exactly 3 input
50
+ channels.
51
+ stackwise_kernel_sizes: list of ints, the kernel sizes used for each
52
+ conv block.
53
+ stackwise_num_repeats: list of ints, number of times to repeat each
54
+ conv block.
55
+ stackwise_input_filters: list of ints, number of input filters for
56
+ each conv block.
57
+ stackwise_output_filters: list of ints, number of output filters for
58
+ each stack in the conv blocks model.
59
+ stackwise_expansion_ratios: list of floats, expand ratio passed to the
60
+ squeeze and excitation blocks.
61
+ stackwise_strides: list of ints, stackwise_strides for each conv block.
62
+ stackwise_squeeze_and_excite_ratios: list of ints, the squeeze and
63
+ excite ratios passed to the squeeze and excitation blocks.
64
+ stackwise_block_types: list of strings. Each value is either 'v1',
65
+ 'unfused' or 'fused' depending on the desired blocks. 'v1' uses the
66
+ original efficientnet block. FusedMBConvBlock is similar to
67
+ MBConvBlock, but instead of using a depthwise convolution and a 1x1
68
+ output convolution blocks fused blocks use a single 3x3 convolution
69
+ block.
70
+ include_rescaling: bool, whether to rescale the inputs. If set to
71
+ True, inputs will be passed through a `Rescaling(1/255.0)` layer.
72
+ min_depth: integer, minimum number of filters. Can be None and ignored
73
+ if use_depth_divisor_as_min_depth is set to True.
74
+ include_initial_padding: bool, whether to include initial zero padding
75
+ (as per v1).
76
+ use_depth_divisor_as_min_depth: bool, whether to use depth_divisor as
77
+ the minimum depth instead of min_depth (as per v1).
78
+ cap_round_filter_decrease: bool, whether to cap the max decrease in the
79
+ number of filters the rounding process potentially produces
80
+ (as per v1).
81
+ stem_conv_padding: str, can be 'same' or 'valid'. Padding for the stem.
82
+ batch_norm_momentum: float, momentum for the moving average calcualtion
83
+ in the batch normalization layers.
84
+
85
+ Example:
86
+ ```python
87
+ # You can customize the EfficientNet architecture:
88
+ model = EfficientNetBackbone(
89
+ stackwise_kernel_sizes=[3, 3, 3, 3, 3, 3],
90
+ stackwise_num_repeats=[2, 4, 4, 6, 9, 15],
91
+ stackwise_input_filters=[24, 24, 48, 64, 128, 160],
92
+ stackwise_output_filters=[24, 48, 64, 128, 160, 256],
93
+ stackwise_expansion_ratios=[1, 4, 4, 4, 6, 6],
94
+ stackwise_squeeze_and_excite_ratios=[0.0, 0.0, 0, 0.25, 0.25, 0.25],
95
+ stackwise_strides=[1, 2, 2, 2, 1, 2],
96
+ stackwise_block_types=[["fused"] * 3 + ["unfused"] * 3],
97
+ width_coefficient=1.0,
98
+ depth_coefficient=1.0,
99
+ include_rescaling=False,
100
+ )
101
+ images = np.ones((1, 256, 256, 3))
102
+ outputs = efficientnet.predict(images)
103
+ ```
104
+ """
105
+
106
+ def __init__(
107
+ self,
108
+ *,
109
+ width_coefficient,
110
+ depth_coefficient,
111
+ stackwise_kernel_sizes,
112
+ stackwise_num_repeats,
113
+ stackwise_input_filters,
114
+ stackwise_output_filters,
115
+ stackwise_expansion_ratios,
116
+ stackwise_squeeze_and_excite_ratios,
117
+ stackwise_strides,
118
+ stackwise_block_types,
119
+ include_rescaling=True,
120
+ dropout=0.2,
121
+ depth_divisor=8,
122
+ min_depth=8,
123
+ input_shape=(None, None, 3),
124
+ activation="swish",
125
+ include_initial_padding=False,
126
+ use_depth_divisor_as_min_depth=False,
127
+ cap_round_filter_decrease=False,
128
+ stem_conv_padding="same",
129
+ batch_norm_momentum=0.9,
130
+ **kwargs,
131
+ ):
132
+ img_input = keras.layers.Input(shape=input_shape)
133
+
134
+ x = img_input
135
+
136
+ if include_rescaling:
137
+ # Use common rescaling strategy across keras
138
+ x = keras.layers.Rescaling(scale=1.0 / 255.0)(x)
139
+
140
+ if include_initial_padding:
141
+ x = keras.layers.ZeroPadding2D(
142
+ padding=self._correct_pad_downsample(x, 3),
143
+ name="stem_conv_pad",
144
+ )(x)
145
+
146
+ # Build stem
147
+ stem_filters = round_filters(
148
+ filters=stackwise_input_filters[0],
149
+ width_coefficient=width_coefficient,
150
+ min_depth=min_depth,
151
+ depth_divisor=depth_divisor,
152
+ use_depth_divisor_as_min_depth=use_depth_divisor_as_min_depth,
153
+ cap_round_filter_decrease=cap_round_filter_decrease,
154
+ )
155
+
156
+ x = keras.layers.Conv2D(
157
+ filters=stem_filters,
158
+ kernel_size=3,
159
+ strides=2,
160
+ padding=stem_conv_padding,
161
+ use_bias=False,
162
+ kernel_initializer=conv_kernel_initializer(),
163
+ name="stem_conv",
164
+ )(x)
165
+
166
+ x = keras.layers.BatchNormalization(
167
+ momentum=batch_norm_momentum,
168
+ name="stem_bn",
169
+ )(x)
170
+ x = keras.layers.Activation(activation, name="stem_activation")(x)
171
+
172
+ # Build blocks
173
+ block_id = 0
174
+ blocks = float(sum(stackwise_num_repeats))
175
+
176
+ self._pyramid_outputs = {}
177
+ curr_pyramid_level = 1
178
+
179
+ for i in range(len(stackwise_kernel_sizes)):
180
+ num_repeats = stackwise_num_repeats[i]
181
+ input_filters = stackwise_input_filters[i]
182
+ output_filters = stackwise_output_filters[i]
183
+
184
+ # Update block input and output filters based on depth multiplier.
185
+ input_filters = round_filters(
186
+ filters=input_filters,
187
+ width_coefficient=width_coefficient,
188
+ min_depth=min_depth,
189
+ depth_divisor=depth_divisor,
190
+ use_depth_divisor_as_min_depth=use_depth_divisor_as_min_depth,
191
+ cap_round_filter_decrease=cap_round_filter_decrease,
192
+ )
193
+ output_filters = round_filters(
194
+ filters=output_filters,
195
+ width_coefficient=width_coefficient,
196
+ min_depth=min_depth,
197
+ depth_divisor=depth_divisor,
198
+ use_depth_divisor_as_min_depth=use_depth_divisor_as_min_depth,
199
+ cap_round_filter_decrease=cap_round_filter_decrease,
200
+ )
201
+
202
+ repeats = round_repeats(
203
+ repeats=num_repeats,
204
+ depth_coefficient=depth_coefficient,
205
+ )
206
+ strides = stackwise_strides[i]
207
+ squeeze_and_excite_ratio = stackwise_squeeze_and_excite_ratios[i]
208
+
209
+ for j in range(repeats):
210
+ # The first block needs to take care of stride and filter size
211
+ # increase.
212
+ if j > 0:
213
+ strides = 1
214
+ input_filters = output_filters
215
+
216
+ if strides != 1:
217
+ self._pyramid_outputs[f"P{curr_pyramid_level}"] = x
218
+ curr_pyramid_level += 1
219
+
220
+ # 97 is the start of the lowercase alphabet.
221
+ letter_identifier = chr(j + 97)
222
+ stackwise_block_type = stackwise_block_types[i]
223
+ block_name = f"block{i + 1}{letter_identifier}_"
224
+ if stackwise_block_type == "v1":
225
+ x = self._apply_efficientnet_block(
226
+ inputs=x,
227
+ filters_in=input_filters,
228
+ filters_out=output_filters,
229
+ kernel_size=stackwise_kernel_sizes[i],
230
+ strides=strides,
231
+ expand_ratio=stackwise_expansion_ratios[i],
232
+ se_ratio=squeeze_and_excite_ratio,
233
+ activation=activation,
234
+ dropout=dropout * block_id / blocks,
235
+ name=block_name,
236
+ )
237
+ else:
238
+ block = get_conv_constructor(stackwise_block_type)(
239
+ input_filters=input_filters,
240
+ output_filters=output_filters,
241
+ expand_ratio=stackwise_expansion_ratios[i],
242
+ kernel_size=stackwise_kernel_sizes[i],
243
+ strides=strides,
244
+ se_ratio=squeeze_and_excite_ratio,
245
+ activation=activation,
246
+ dropout=dropout * block_id / blocks,
247
+ batch_norm_momentum=batch_norm_momentum,
248
+ name=block_name,
249
+ )
250
+ x = block(x)
251
+ block_id += 1
252
+
253
+ # Build top
254
+ top_filters = round_filters(
255
+ filters=1280,
256
+ width_coefficient=width_coefficient,
257
+ min_depth=min_depth,
258
+ depth_divisor=depth_divisor,
259
+ use_depth_divisor_as_min_depth=use_depth_divisor_as_min_depth,
260
+ cap_round_filter_decrease=cap_round_filter_decrease,
261
+ )
262
+
263
+ x = keras.layers.Conv2D(
264
+ filters=top_filters,
265
+ kernel_size=1,
266
+ padding="same",
267
+ strides=1,
268
+ kernel_initializer=conv_kernel_initializer(),
269
+ use_bias=False,
270
+ name="top_conv",
271
+ data_format="channels_last",
272
+ )(x)
273
+ x = keras.layers.BatchNormalization(
274
+ momentum=batch_norm_momentum,
275
+ name="top_bn",
276
+ )(x)
277
+ x = keras.layers.Activation(
278
+ activation=activation, name="top_activation"
279
+ )(x)
280
+
281
+ self._pyramid_outputs[f"P{curr_pyramid_level}"] = x
282
+ curr_pyramid_level += 1
283
+
284
+ # Create model.
285
+ super().__init__(inputs=img_input, outputs=x, **kwargs)
286
+
287
+ # === Config ===
288
+ self.include_rescaling = include_rescaling
289
+ self.width_coefficient = width_coefficient
290
+ self.depth_coefficient = depth_coefficient
291
+ self.dropout = dropout
292
+ self.depth_divisor = depth_divisor
293
+ self.min_depth = min_depth
294
+ self.activation = activation
295
+ self.stackwise_kernel_sizes = stackwise_kernel_sizes
296
+ self.stackwise_num_repeats = stackwise_num_repeats
297
+ self.stackwise_input_filters = stackwise_input_filters
298
+ self.stackwise_output_filters = stackwise_output_filters
299
+ self.stackwise_expansion_ratios = stackwise_expansion_ratios
300
+ self.stackwise_squeeze_and_excite_ratios = (
301
+ stackwise_squeeze_and_excite_ratios
302
+ )
303
+ self.stackwise_strides = stackwise_strides
304
+ self.stackwise_block_types = stackwise_block_types
305
+
306
+ self.include_initial_padding = include_initial_padding
307
+ self.use_depth_divisor_as_min_depth = use_depth_divisor_as_min_depth
308
+ self.cap_round_filter_decrease = cap_round_filter_decrease
309
+ self.stem_conv_padding = stem_conv_padding
310
+ self.batch_norm_momentum = batch_norm_momentum
311
+
312
+ def get_config(self):
313
+ config = super().get_config()
314
+ config.update(
315
+ {
316
+ "include_rescaling": self.include_rescaling,
317
+ "width_coefficient": self.width_coefficient,
318
+ "depth_coefficient": self.depth_coefficient,
319
+ "dropout": self.dropout,
320
+ "depth_divisor": self.depth_divisor,
321
+ "min_depth": self.min_depth,
322
+ "activation": self.activation,
323
+ "input_shape": self.input_shape[1:],
324
+ "stackwise_kernel_sizes": self.stackwise_kernel_sizes,
325
+ "stackwise_num_repeats": self.stackwise_num_repeats,
326
+ "stackwise_input_filters": self.stackwise_input_filters,
327
+ "stackwise_output_filters": self.stackwise_output_filters,
328
+ "stackwise_expansion_ratios": self.stackwise_expansion_ratios,
329
+ "stackwise_squeeze_and_excite_ratios": self.stackwise_squeeze_and_excite_ratios,
330
+ "stackwise_strides": self.stackwise_strides,
331
+ "stackwise_block_types": self.stackwise_block_types,
332
+ "include_initial_padding": self.include_initial_padding,
333
+ "use_depth_divisor_as_min_depth": self.use_depth_divisor_as_min_depth,
334
+ "cap_round_filter_decrease": self.cap_round_filter_decrease,
335
+ "stem_conv_padding": self.stem_conv_padding,
336
+ "batch_norm_momentum": self.batch_norm_momentum,
337
+ }
338
+ )
339
+ return config
340
+
341
+ def _correct_pad_downsample(self, inputs, kernel_size):
342
+ """Returns a tuple for zero-padding for 2D convolution with downsampling.
343
+
344
+ Args:
345
+ inputs: Input tensor.
346
+ kernel_size: An integer or tuple/list of 2 integers.
347
+
348
+ Returns:
349
+ A tuple.
350
+ """
351
+ img_dim = 1
352
+ input_size = inputs.shape[img_dim : (img_dim + 2)]
353
+ if isinstance(kernel_size, int):
354
+ kernel_size = (kernel_size, kernel_size)
355
+ if input_size[0] is None:
356
+ adjust = (1, 1)
357
+ else:
358
+ adjust = (1 - input_size[0] % 2, 1 - input_size[1] % 2)
359
+ correct = (kernel_size[0] // 2, kernel_size[1] // 2)
360
+ return (
361
+ (correct[0] - adjust[0], correct[0]),
362
+ (correct[1] - adjust[1], correct[1]),
363
+ )
364
+
365
+ def _apply_efficientnet_block(
366
+ self,
367
+ inputs,
368
+ filters_in=32,
369
+ filters_out=16,
370
+ kernel_size=3,
371
+ strides=1,
372
+ activation="swish",
373
+ expand_ratio=1,
374
+ se_ratio=0.0,
375
+ dropout=0.0,
376
+ name="",
377
+ ):
378
+ """An inverted residual block.
379
+
380
+ Args:
381
+ inputs: Tensor, The input tensor of the block
382
+ filters_in: integer, the number of input filters.
383
+ filters_out: integer, the number of output filters.
384
+ kernel_size: integer, the dimension of the convolution window.
385
+ strides: integer, the stride of the convolution.
386
+ activation: activation function to use between each convolutional layer.
387
+ expand_ratio: integer, scaling coefficient for the input filters.
388
+ se_ratio: float between 0 and 1, fraction to squeeze the input filters.
389
+ dropout: float between 0 and 1, fraction of the input units to drop.
390
+ name: string, block label.
391
+
392
+ Returns:
393
+ output tensor for the block.
394
+ """
395
+ filters = filters_in * expand_ratio
396
+ if expand_ratio != 1:
397
+ x = keras.layers.Conv2D(
398
+ filters=filters,
399
+ kernel_size=1,
400
+ strides=1,
401
+ padding="same",
402
+ use_bias=False,
403
+ kernel_initializer=conv_kernel_initializer(),
404
+ name=name + "expand_conv",
405
+ )(inputs)
406
+ x = keras.layers.BatchNormalization(
407
+ axis=3,
408
+ name=name + "expand_bn",
409
+ )(x)
410
+ x = keras.layers.Activation(
411
+ activation, name=name + "expand_activation"
412
+ )(x)
413
+ else:
414
+ x = inputs
415
+
416
+ # Depthwise Convolution
417
+ if strides == 2:
418
+ x = keras.layers.ZeroPadding2D(
419
+ padding=self._correct_pad_downsample(x, kernel_size),
420
+ name=name + "dwconv_pad",
421
+ )(x)
422
+ conv_pad = "valid"
423
+ else:
424
+ conv_pad = "same"
425
+
426
+ x = keras.layers.DepthwiseConv2D(
427
+ kernel_size=kernel_size,
428
+ strides=strides,
429
+ padding=conv_pad,
430
+ use_bias=False,
431
+ depthwise_initializer=conv_kernel_initializer(),
432
+ name=name + "dwconv",
433
+ )(x)
434
+ x = keras.layers.BatchNormalization(
435
+ axis=3,
436
+ name=name + "dwconv_bn",
437
+ )(x)
438
+ x = keras.layers.Activation(
439
+ activation, name=name + "dwconv_activation"
440
+ )(x)
441
+
442
+ # Squeeze and Excitation phase
443
+ if 0 < se_ratio <= 1:
444
+ filters_se = max(1, int(filters_in * se_ratio))
445
+ se = keras.layers.GlobalAveragePooling2D(name=name + "se_squeeze")(
446
+ x
447
+ )
448
+ se_shape = (1, 1, filters)
449
+ se = keras.layers.Reshape(se_shape, name=name + "se_reshape")(se)
450
+ se = keras.layers.Conv2D(
451
+ filters_se,
452
+ 1,
453
+ padding="same",
454
+ activation=activation,
455
+ kernel_initializer=conv_kernel_initializer(),
456
+ name=name + "se_reduce",
457
+ )(se)
458
+ se = keras.layers.Conv2D(
459
+ filters,
460
+ 1,
461
+ padding="same",
462
+ activation="sigmoid",
463
+ kernel_initializer=conv_kernel_initializer(),
464
+ name=name + "se_expand",
465
+ )(se)
466
+ x = keras.layers.multiply([x, se], name=name + "se_excite")
467
+
468
+ # Output phase
469
+ x = keras.layers.Conv2D(
470
+ filters=filters_out,
471
+ kernel_size=1,
472
+ strides=1,
473
+ padding="same",
474
+ use_bias=False,
475
+ kernel_initializer=conv_kernel_initializer(),
476
+ name=name + "project",
477
+ )(x)
478
+ x = keras.layers.BatchNormalization(
479
+ axis=3,
480
+ name=name + "project_bn",
481
+ )(x)
482
+ x = keras.layers.Activation(
483
+ activation, name=name + "project_activation"
484
+ )(x)
485
+
486
+ if strides == 1 and filters_in == filters_out:
487
+ if dropout > 0:
488
+ x = keras.layers.Dropout(
489
+ dropout,
490
+ noise_shape=(None, 1, 1, 1),
491
+ name=name + "drop",
492
+ )(x)
493
+ x = keras.layers.Add(name=name + "add")([x, inputs])
494
+
495
+ return x
496
+
497
+
498
+ def conv_kernel_initializer(scale=2.0):
499
+ return keras.initializers.VarianceScaling(
500
+ scale=scale, mode="fan_out", distribution="truncated_normal"
501
+ )
502
+
503
+
504
+ def round_filters(
505
+ filters,
506
+ width_coefficient,
507
+ min_depth,
508
+ depth_divisor,
509
+ use_depth_divisor_as_min_depth,
510
+ cap_round_filter_decrease,
511
+ ):
512
+ """Round number of filters based on depth multiplier.
513
+
514
+ Args:
515
+ filters: int, number of filters for Conv layer
516
+ width_coefficient: float, denotes the scaling coefficient of network
517
+ width
518
+ depth_divisor: int, a unit of network width
519
+ use_depth_divisor_as_min_depth: bool, whether to use depth_divisor as
520
+ the minimum depth instead of min_depth (as per v1)
521
+ max_round_filter_decrease: bool, whether to cap the decrease in the
522
+ number of filters this process produces (as per v1)
523
+
524
+ Returns:
525
+ int, new rounded filters value for Conv layer
526
+ """
527
+ filters *= width_coefficient
528
+
529
+ if use_depth_divisor_as_min_depth:
530
+ min_depth = depth_divisor
531
+
532
+ new_filters = max(
533
+ min_depth,
534
+ int(filters + depth_divisor / 2) // depth_divisor * depth_divisor,
535
+ )
536
+
537
+ if cap_round_filter_decrease:
538
+ # Make sure that round down does not go down by more than 10%.
539
+ if new_filters < 0.9 * filters:
540
+ new_filters += depth_divisor
541
+
542
+ return int(new_filters)
543
+
544
+
545
+ def round_repeats(repeats, depth_coefficient):
546
+ """Round number of repeats based on depth multiplier.
547
+
548
+ Args:
549
+ repeats: int, number of repeats of efficientnet block
550
+ depth_coefficient: float, denotes the scaling coefficient of network
551
+ depth
552
+
553
+ Returns:
554
+ int, rounded repeats
555
+ """
556
+ return int(math.ceil(depth_coefficient * repeats))
557
+
558
+
559
+ def get_conv_constructor(conv_type):
560
+ if conv_type == "unfused":
561
+ return MBConvBlock
562
+ elif conv_type == "fused":
563
+ return FusedMBConvBlock
564
+ else:
565
+ raise ValueError(
566
+ "Expected `conv_type` to be "
567
+ "one of 'unfused', 'fused', but got "
568
+ f"`conv_type={conv_type}`"
569
+ )