This release is a pre-release and may not be stable for production use.
fuse-augmentations
Fuse consecutive geometric augmentation ops (rotation, scale, shear, flip) into a single grid_sample pass, eliminating redundant interpolation and improving image quality.
Drop-in replacement for Kornia's AugmentationSequential / Sequential - same call interface, fewer warps.
Installation
pip install fuse-augmentations
Requires: Python 3.10+, PyTorch 2.1+. Kornia and TorchVision are optional (needed only when passing Kornia or TorchVision transform objects). Install extras: pip install fuse-augmentations[kornia] or pip install fuse-augmentations[torchvision].
Quick start
import torch
import kornia.augmentation as K
from fuse_aug import Compose
pipe = Compose(
[
K.RandomRotation(degrees=30, p=0.8),
K.RandomHorizontalFlip(p=0.5),
K.RandomAffine(degrees=0, scale=(0.8, 1.2), p=0.7),
]
)
image = torch.rand(4, 3, 256, 256) # (B, C, H, W)
out = pipe(image) # one grid_sample instead of three
TorchVision backend
Works with both torchvision.transforms (v1) and torchvision.transforms.v2:
import torchvision.transforms.v2 as T
from fuse_aug import Compose
pipe = Compose([T.RandomRotation(degrees=30), T.RandomHorizontalFlip(p=0.5)])
out = pipe(image) # one grid_sample instead of two
Mixed backends (Kornia + TorchVision in the same pipeline) are also supported.
Auxiliary targets - masks, boxes, keypoints
Pass data_keys to route auxiliary tensors through the same fused transform:
from fuse_aug import Compose
import kornia.augmentation as K
pipe = Compose(
[
K.RandomRotation(degrees=30, p=0.8),
K.RandomHorizontalFlip(p=0.5),
],
data_keys=["input", "mask"],
)
img_out, mask_out = pipe(image, mask) # mask warped with mode='nearest'
Supported keys:
| Key | Tensor shape | Notes |
|---|---|---|
"input" |
(B, C, H, W) |
Image; always the first argument |
"mask" |
(B, C, H, W) |
Nearest-neighbour sampling; integer class labels preserved |
"bbox_xyxy" |
(B, N, 4) |
Pixel-space [x1, y1, x2, y2]; AABB wrapping after rotation |
"bbox_xywh" |
(B, N, 4) |
Pixel-space [x, y, w, h]; converted internally to xyxy and back |
"keypoints" |
(B, N, 2) |
Pixel-space [x, y]; exact homogeneous transform, no AABB |
Bounding boxes and keypoints use the composed forward matrix; masks share the same sampling grid as the image.
Backend-free pipelines with from_params
Construct a fused pipeline from numeric parameter ranges - no Kornia import required:
from fuse_aug import Compose
pipe = Compose.from_params(rotation=(-30, 30), scale=(0.8, 1.2), hflip_p=0.5)
out = pipe(image)
from_params accepts: rotation, scale, scale_x, scale_y, shear_x, shear_y, translate_x, translate_y, hflip_p, vflip_p, interpolation, padding_mode, reorder, and data_keys.
How fusion works
Given a pipeline [Rotate, Scale, HFlip, GaussianBlur, Rotate]:
[Rotate, Scale, HFlip]are grouped into aFusedAffineSegment- their matrices are composed and onegrid_samplecall is made.GaussianBluris a spatial-kernel barrier - it passes through unchanged.- The trailing
Rotateforms its ownFusedAffineSegment.
print(pipe.fusion_plan)
# fused(RandomRotation, RandomResizedCrop, RandomHorizontalFlip) -> passthrough(RandomGaussianBlur) -> fused(RandomRotation)
print(pipe.n_warps_saved)
# 2 (saved 2 interpolation passes)
Reorder policy
from fuse_aug import Compose, ReorderPolicy
import kornia.augmentation as K
pipe = Compose(
[
K.RandomRotation(degrees=15, p=0.8),
K.ColorJitter(brightness=0.3, p=0.5), # POINTWISE
K.RandomHorizontalFlip(p=0.5),
],
reorder=ReorderPolicy.POINTWISE,
)
# ColorJitter is moved after HFlip, letting both geometric ops fuse:
# fused(RandomRotation, RandomHorizontalFlip) -> passthrough(ColorJitter)
Transform matrix access
out = pipe(image)
M = pipe.transform_matrix # (B, 3, 3) composed forward matrix
Use M to transform stored coordinates (keypoints, boxes) that were not passed as data_keys.
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distributions
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file fuse_augmentations-0.5.0.dev0-py3-none-any.whl.
File metadata
- Download URL: fuse_augmentations-0.5.0.dev0-py3-none-any.whl
- Upload date:
- Size: 50.2 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via:
twine/6.2.0 CPython/3.12.13
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
c22e03f0c92c531e4f71abf137d53cde89a4b07214e1a849a388727475a210ad
|
|
| MD5 |
e7c5451f59ea9302043821e5af8c4851
|
|
| BLAKE2b-256 |
6e98ee5388bffcd18c98a406b9c81fd02908f5261b745d480da358f76af0dfbc
|