Equimo 0.4.6a2__tar.gz → 0.4.6a3__tar.gz
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.
- {equimo-0.4.6a2/src/Equimo.egg-info → equimo-0.4.6a3}/PKG-INFO +1 -1
- {equimo-0.4.6a2 → equimo-0.4.6a3}/pyproject.toml +1 -1
- {equimo-0.4.6a2 → equimo-0.4.6a3/src/Equimo.egg-info}/PKG-INFO +1 -1
- equimo-0.4.6a3/src/equimo/__init__.py +1 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/convolution.py +45 -18
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/wavelet.py +24 -10
- equimo-0.4.6a2/src/equimo/__init__.py +0 -1
- {equimo-0.4.6a2 → equimo-0.4.6a3}/LICENSE.md +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/README.md +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/setup.cfg +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/Equimo.egg-info/SOURCES.txt +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/Equimo.egg-info/dependency_links.txt +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/Equimo.egg-info/requires.txt +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/Equimo.egg-info/top_level.txt +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/conversion/__init__.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/conversion/utils.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/experimental/__init__.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/experimental/text.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/io.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/__init__.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/activation.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/attention.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/downsample.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/dropout.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/ffn.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/generic.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/mamba.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/norm.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/patch.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/posemb.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/sharing.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/layers/squeeze_excite.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/models/__init__.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/models/emamodel.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/models/fastervit.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/models/lowformer.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/models/mlla.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/models/partialformer.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/models/reduceformer.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/models/shvit.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/models/vit.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/models/vssd.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/ops/scan.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/src/equimo/utils.py +0 -0
- {equimo-0.4.6a2 → equimo-0.4.6a3}/tests/test_models.py +0 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
__version__ = "0.4.6a3"
|
|
@@ -1300,16 +1300,33 @@ class GenericGhostModule(eqx.Module):
|
|
|
1300
1300
|
inference: Optional[bool] = None,
|
|
1301
1301
|
):
|
|
1302
1302
|
use_inference = self.inference if inference is None else inference
|
|
1303
|
-
|
|
1303
|
+
use_inference = jnp.asarray(use_inference, dtype=bool)
|
|
1304
1304
|
|
|
1305
|
-
|
|
1306
|
-
|
|
1307
|
-
|
|
1305
|
+
out = jax.lax.cond(
|
|
1306
|
+
use_inference,
|
|
1307
|
+
lambda x_: self.inference_features(x_),
|
|
1308
|
+
lambda x_: self.training_features(x_),
|
|
1309
|
+
operand=x,
|
|
1310
|
+
)
|
|
1311
|
+
|
|
1312
|
+
shortcut_pred = bool(self.mode == "shortcut")
|
|
1313
|
+
|
|
1314
|
+
def _shortcut_branch(ox):
|
|
1315
|
+
out_, x_ = ox
|
|
1316
|
+
res = self.short_conv(self.pool2(x_))
|
|
1317
|
+
gating = jax.image.resize(
|
|
1308
1318
|
image=jax.nn.sigmoid(res / self.gate_scale),
|
|
1309
|
-
shape=(res.shape[0],
|
|
1319
|
+
shape=(res.shape[0], out_.shape[1], out_.shape[2]),
|
|
1310
1320
|
method="nearest",
|
|
1311
1321
|
)
|
|
1312
|
-
|
|
1322
|
+
return out_[: self.out_channels, :, :] * gating
|
|
1323
|
+
|
|
1324
|
+
out = jax.lax.cond(
|
|
1325
|
+
shortcut_pred,
|
|
1326
|
+
_shortcut_branch,
|
|
1327
|
+
lambda ox: ox[0],
|
|
1328
|
+
operand=(out, x),
|
|
1329
|
+
)
|
|
1313
1330
|
|
|
1314
1331
|
return out
|
|
1315
1332
|
|
|
@@ -1347,7 +1364,6 @@ class GhostBottleneck(eqx.Module):
|
|
|
1347
1364
|
stride: int = 1,
|
|
1348
1365
|
act_layer: Callable = jax.nn.relu,
|
|
1349
1366
|
se_ratio: float = 0.0,
|
|
1350
|
-
layer_id: Optional[int] = None,
|
|
1351
1367
|
use_shortcut_mode_in_ghost1: bool = True,
|
|
1352
1368
|
allow_identity_residual: bool = True,
|
|
1353
1369
|
key: PRNGKeyArray,
|
|
@@ -1490,30 +1506,41 @@ class GhostBottleneck(eqx.Module):
|
|
|
1490
1506
|
inference: Optional[bool] = None,
|
|
1491
1507
|
) -> Float[Array, "channels height width"]:
|
|
1492
1508
|
use_inference = self.inference if inference is None else inference
|
|
1493
|
-
|
|
1509
|
+
use_inference = jax.numpy.asarray(use_inference, dtype=bool)
|
|
1494
1510
|
|
|
1511
|
+
k_g1, k_g2 = jr.split(key, 2)
|
|
1495
1512
|
residual = x
|
|
1496
1513
|
|
|
1497
1514
|
x = self.ghost1(x, key=k_g1, inference=use_inference)
|
|
1498
1515
|
|
|
1499
1516
|
if self.stride > 1:
|
|
1500
|
-
|
|
1501
|
-
|
|
1502
|
-
|
|
1503
|
-
|
|
1504
|
-
|
|
1505
|
-
|
|
1506
|
-
|
|
1507
|
-
|
|
1517
|
+
x = jax.lax.cond(
|
|
1518
|
+
use_inference,
|
|
1519
|
+
lambda y: self.dw_shared_norm(self.dw_conv(y)),
|
|
1520
|
+
lambda y: self.dw_shared_norm(
|
|
1521
|
+
jax.tree_util.tree_reduce(
|
|
1522
|
+
operator.add,
|
|
1523
|
+
(
|
|
1524
|
+
(
|
|
1525
|
+
[]
|
|
1526
|
+
if isinstance(self.dw_rpr_scale, eqx.nn.Identity)
|
|
1527
|
+
else [self.dw_rpr_scale(y)]
|
|
1528
|
+
)
|
|
1529
|
+
+ [conv(y) for conv in self.dw_rpr_conv]
|
|
1530
|
+
),
|
|
1531
|
+
)
|
|
1532
|
+
),
|
|
1533
|
+
operand=x,
|
|
1534
|
+
)
|
|
1508
1535
|
|
|
1509
1536
|
x = self.se(x)
|
|
1510
1537
|
|
|
1511
1538
|
x = self.ghost2(x, key=k_g2, inference=use_inference)
|
|
1512
1539
|
|
|
1513
1540
|
if not isinstance(self.shortcut, eqx.nn.Identity):
|
|
1514
|
-
x
|
|
1541
|
+
x = x + self.shortcut(residual)
|
|
1515
1542
|
elif self.allow_identity_residual:
|
|
1516
|
-
x
|
|
1543
|
+
x = x + residual
|
|
1517
1544
|
|
|
1518
1545
|
return x
|
|
1519
1546
|
|
|
@@ -63,7 +63,7 @@ def haar_dwt_split(
|
|
|
63
63
|
|
|
64
64
|
|
|
65
65
|
class HWDConv(eqx.Module):
|
|
66
|
-
mode: Literal["h_discard", "accurate"] = eqx.field(static=True)
|
|
66
|
+
mode: Literal["h_discard", "band_grouped", "accurate"] = eqx.field(static=True)
|
|
67
67
|
|
|
68
68
|
pre_norm: eqx.nn.GroupNorm
|
|
69
69
|
proj: eqx.nn.Conv2d
|
|
@@ -78,31 +78,43 @@ class HWDConv(eqx.Module):
|
|
|
78
78
|
kernel_size: int = 1,
|
|
79
79
|
use_bias: bool = False,
|
|
80
80
|
act: Callable = jax.nn.relu,
|
|
81
|
-
mode: Literal["h_discard", "accurate"] = "accurate",
|
|
81
|
+
mode: Literal["h_discard", "band_grouped", "accurate"] = "accurate",
|
|
82
82
|
dropout: float = 0.0,
|
|
83
83
|
key: PRNGKeyArray,
|
|
84
84
|
):
|
|
85
85
|
self.mode = mode
|
|
86
86
|
|
|
87
|
-
# Channels entering the projection (and thus the pre-norm)
|
|
88
87
|
channels_in = in_channels if mode == "h_discard" else 4 * in_channels
|
|
89
88
|
|
|
90
|
-
#
|
|
91
|
-
#
|
|
92
|
-
# For h_discard mode: total_groups = groups_per_band (single band).
|
|
89
|
+
# GroupNorm: align groups to sub-band boundaries
|
|
90
|
+
# groups_per_band divides in_channels; total_groups = 4 * groups_per_band for 4 bands
|
|
93
91
|
groups_per_band = nearest_power_of_2_divisor(in_channels, 32)
|
|
94
92
|
total_groups = groups_per_band if mode == "h_discard" else 4 * groups_per_band
|
|
95
|
-
|
|
96
93
|
self.pre_norm = eqx.nn.GroupNorm(channels=channels_in, groups=total_groups)
|
|
97
94
|
|
|
95
|
+
# Projection 1x1 conv
|
|
96
|
+
# - accurate: dense projection (groups=1)
|
|
97
|
+
# - band_grouped: independent per-band projections (groups=4), no cross-band mixing
|
|
98
|
+
# - h_discard: single-band dense projection (groups=1)
|
|
99
|
+
proj_groups = 1
|
|
100
|
+
if mode == "band_grouped":
|
|
101
|
+
if out_channels % 4 != 0:
|
|
102
|
+
raise ValueError(
|
|
103
|
+
"band_grouped mode requires out_channels to be divisible by 4 "
|
|
104
|
+
"so each sub-band produces an equal share."
|
|
105
|
+
)
|
|
106
|
+
proj_groups = 4
|
|
107
|
+
|
|
98
108
|
self.proj = eqx.nn.Conv2d(
|
|
99
|
-
channels_in,
|
|
100
|
-
out_channels,
|
|
109
|
+
in_channels=channels_in,
|
|
110
|
+
out_channels=out_channels,
|
|
101
111
|
kernel_size=kernel_size,
|
|
102
112
|
use_bias=use_bias,
|
|
103
113
|
padding="SAME",
|
|
114
|
+
groups=proj_groups,
|
|
104
115
|
key=key,
|
|
105
116
|
)
|
|
117
|
+
|
|
106
118
|
self.act = act
|
|
107
119
|
|
|
108
120
|
self.dropout = eqx.nn.Dropout(dropout)
|
|
@@ -115,11 +127,13 @@ class HWDConv(eqx.Module):
|
|
|
115
127
|
if self.mode == "h_discard":
|
|
116
128
|
y = LL # (C, H/2, W/2)
|
|
117
129
|
else:
|
|
130
|
+
# Keep sub-bands contiguous and ordered so GN groups and grouped conv line up
|
|
118
131
|
y = jnp.concatenate([LL, HL, LH, HH], axis=0) # (4*C, H/2, W/2)
|
|
119
132
|
|
|
133
|
+
# Band-aligned normalization (no cross-band statistics)
|
|
120
134
|
y = self.pre_norm(y)
|
|
121
135
|
|
|
122
|
-
y = self.proj(y) # (
|
|
136
|
+
y = self.proj(y) # (out_channels, H/2, W/2)
|
|
123
137
|
y = self.act(y)
|
|
124
138
|
|
|
125
139
|
y = self.dropout(y, inference=inference, key=key)
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
__version__ = "0.4.6a2"
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|