albumentations-team / albumentations

Fast and flexible image augmentation library. Paper about the library: https://www.mdpi.com/2078-2489/11/2/125
https://albumentations.ai
MIT License
14.19k stars 1.65k forks source link

PadIfNeeded taking long time when it doesnt need to pad #944

Closed blaine141 closed 3 months ago

blaine141 commented 3 years ago

I have discovered that PadIfNeeded has some bug slowing it down. I have an application where I had PadIfNeeded just in case. It never had to pad any of my samples as they were all big enough, but still introduced a 150ms delay in the augmentation. I imagine it should not take 150ms to just check the dimensions of the input. Here is the Augmentation I am using. With PadIfNeeded it takes 0.25 seconds. Without PadIfNeeded it takes 0.1 seconds.

train_transform = [

        A.PadIfNeeded(min_height=BIGGEST_CROP_NEEDED[0], min_width=BIGGEST_CROP_NEEDED[1]),
        A.RandomCrop(height=BIGGEST_CROP_NEEDED[0], width=BIGGEST_CROP_NEEDED[1]),

        A.ShiftScaleRotate(scale_limit=0.2, rotate_limit=180,
                              shift_limit=0, p=1),

        A.CenterCrop(height=TRAIN_SIZE[0], width=TRAIN_SIZE[1]),

        A.GaussNoise(p=0.2),
        A.HorizontalFlip(p=0.5),

        # A.OneOf(
        #     [
        #         A.CLAHE(p=1),
        #         A.RandomBrightnessContrast(p=1, contrast_limit=0),
        #         A.RandomGamma(p=1),
        #     ],
        #     p=0.9,
        # ),

        A.OneOf(
            [
                A.Sharpen(p=1),
                A.Blur(p=1),
                A.MotionBlur(p=1),
            ],
            p=0.9,
        ),

        # A.OneOf(
        #     [
        #         A.RandomBrightnessContrast(p=1, brightness_limit=0),
        #         A.HueSaturationValue(p=1),
        #     ],
        #     p=0.9,
        # ),

        A.Lambda(image=modality_dropout)
]
return A.Compose(train_transform)

I haven't looked that much into the issue since I don't need PadIfNecessary, just thought I'd share.

BloodAxe commented 3 years ago

Would you mind sharing your measurement code so we compare apples to apples?

Dipet commented 3 years ago

Looks like OpenCV function CopyMakeBorder always creates copy of image.

import cv2 as cv
import numpy as np
import time

img = np.empty([512, 512, 3], dtype=np.uint8)
res = cv.copyMakeBorder(img, 0, 0, 0, 0, cv.BORDER_CONSTANT, value=0)
id(res), id(img), id(res) == id(img)
# (140702040314624, 140702040316144, False)