Open CMCDragonkai opened 6 years ago
iaa.SomeOf((1, 3), [iaa.Dropout(...), iaa.Affine(...), iaa.AdditiveGaussianNoise()])
would always apply 1 to 3 of the 3 augmenters (i.e. at least one).
iaa.OneOf([iaa.Dropout(...), iaa.Affine(...), iaa.AdditiveGaussianNoise()])
always applies exactly 1 of the 3 augmenters.
iaa.Sequential([iaa.Dropout(...), iaa.Affine(...), iaa.AdditiveGaussianNoise()])
always apply 3 of the 3 augmenters.
If you use Sometimes or augmenters with probabilities (e.g. Invert), there is always a small chance that none of them will be applied. This can currently only be avoided if you add some other augmenters of which at least one is always applied (using above methods).
I've taken your advice, but I've detected that no augmentation can still happen with:
iaa.SomeOf((1, None) ...)
Everything else works, except after checking the output augmentations, I found no augmentation was applied to one specific image. This image is nothing special. Testing in isolation allowed me to augment the image normally. It's just as I used it a batch of many images, a single image kept not being augmented.
I created an "augmentation schema" which I apply:
{
"augs": [{
"type": "Fliplr",
"args": [1.0]
},
{
"type": "Flipud",
"args": [1.0]
},
{
"type": "CropAndPad",
"kwargs": {
"percent": [-0.25, 0.25],
"pad_mode": "constant"
}
},
{
"type": "Multiply",
"args": [
[0.9, 1.1]
],
"kwargs": {
"per_channel": 0.5,
"name": "Multiply"
}
},
{
"type": "GaussianBlur",
"kwargs": {
"sigma": [0, 0.1],
"name": "GaussianBlur"
}
},
{
"type": "AdditiveGaussianNoise",
"kwargs": {
"scale": [0, 5.1],
"per_channel": true,
"name": "AdditiveGaussianNoise"
}
},
{
"type": "Affine",
"kwargs": {
"scale": {
"x": [0.8, 1.2],
"y": [0.8, 1.2]
},
"translate_percent": {
"x": [-0.2, 0.2],
"y": [-0.2, 0.2]
},
"rotate": [-50, 50],
"shear": [-8, 8],
"order": 3,
"mode": "constant"
}
}
],
"mask_filter": ["Multiply", "GaussianBlur", "AdditiveGaussianNoise"]
}
def parse_aug_config(config_file):
aug_config = json.load(config_file, cls=AugmentationDecoder)
augs = []
for aug in aug_config['augs']:
aug_constructor = getattr(iaa, aug['type'])
aug_args = aug.get('args', [])
aug_kwargs = aug.get('kwargs', {})
augs.append(aug_constructor(*aug_args, **aug_kwargs))
augs_mask_filter = aug_config['mask_filter']
aug_pipeline_template = iaa.SomeOf((1, None), augs, random_order=True)
def masks_activator(images, augmenter, parents, default):
if augmenter.name in augs_mask_filter:
return False
else:
return default
masks_hook = ia.HooksImages(activator=masks_activator)
return (aug_pipeline_template, masks_hook)
def augment_image_mask(image, mask, aug_pipeline_template, masks_hook):
aug_pipeline = aug_pipeline_template.to_deterministic()
if mask is not None:
(image_aug, *_) = aug_pipeline.augment_images(np.array([image]))
(mask_aug, *_) = aug_pipeline.augment_images(
np.array([mask]), hooks=masks_hook)
else:
(image_aug, *_) = aug_pipeline.augment_images(np.array([image]))
mask_aug = None
return (image_aug, mask_aug)
I'm running imgaug 0.2.6.
Are you sure there's no way that iaa.SomeOf
especially with the augmentations that I'm using that 0 augmentations may be applied?
Your json code contains a lot of lists for parameter ranges, e.g. "sigma": [0, 0.1]
. These are parsed by json.load
as lists and provided to the augmenter constructors without changes. The augmenters then interpret these parameters as lists of allowed values and pick randomly from these lists. So for the above sigma
example you would get either 0
or 0.1
sampled, but not anything in between. To get a uniform distribution, you have to provide either (0, 0.1)
(i.e. a tuple) or imgaug.parameters.Uniform(0, 0.1)
as a parameter.
There is of course also a chance that a uniform distribution randomly sampled 0
or 0.1
.
btw
(image_aug, *_) = aug_pipeline.augment_images(np.array([image]))
can probably be replaced by
image_aug = aug_pipeline.augment_image(np.array([image]))
Oh... well JSON only has lists, I wonder what's a good way to integrate the difference between lists and tuples in our augmentation schema.
I think the best way for now is always interpret the lists as tuples, as that was what I originally was doing before I extracted the code into a JSON schema.
It seems there's always a chance of no augmentation applied. Is it possible to make sure that at least 1 random augmentation is applied?