Detect which image is sharper

后端 未结 5 1446
情话喂你
情话喂你 2020-12-07 18:56

I\'m looking for a way to detect which of two (similar) images is sharper.

I\'m thinking this could be using some measure of overall sharpness and generating a score

相关标签:
5条回答
  • 2020-12-07 19:37

    This paper describes a method for computing a blur factor using DWT. Looked pretty straight forward but instead of detecting sharpness it's detecting blurredness. Seems it detects edges first (simple convolution) and then uses DWT to accumulate and score it.

    0 讨论(0)
  • 2020-12-07 19:43

    The simple method is to measure contrast -- the image with the largest differences between pixel values is the sharpest. You can, for example, compute the variance (or standard deviation) of the pixel values, and whichever produces the larger number wins. That looks for maximum overall contrast, which may not be what you want though -- in particular, it will tend to favor pictures with maximum depth of field.

    Depending on what you want, you may prefer to use something like an FFT, to see which displays the highest frequency content. This allows you to favor a picture that's extremely sharp in some parts (but less so in others) over one that has more depth of field, so more of the image is reasonably sharp, but the maximum sharpness is lower (which is common, due to diffraction with smaller apertures).

    0 讨论(0)
  • 2020-12-07 19:47

    Simple practical approach would be to use edge detection (more edges == sharper image).

    Quick and dirty hands-on using PHP GD

    function getBlurAmount($image) {
        $size = getimagesize($image);
        $image = imagecreatefromjpeg($image);
        imagefilter($image, IMG_FILTER_EDGEDETECT);    
        $blur = 0;
        for ($x = 0; $x < $size[0]; $x++) {
            for ($y = 0; $y < $size[1]; $y++) {
                $blur += imagecolorat($image, $x, $y) & 0xFF;
            }
        }
        return $blur;
    }
    
    $e1 = getBlurAmount('http://upload.wikimedia.org/wikipedia/commons/thumb/5/51/Jonquil_flowers_at_f32.jpg/800px-Jonquil_flowers_at_f32.jpg');
    $e2 = getBlurAmount('http://upload.wikimedia.org/wikipedia/commons/thumb/0/01/Jonquil_flowers_at_f5.jpg/800px-Jonquil_flowers_at_f5.jpg');
    
    echo "Relative blur amount: first image " . $e1 / min($e1, $e2) . ", second image " . $e2 / min($e1, $e2);
    

    (image with less blur is sharper) More efficient approach would be to detect edges in your code, using Sobel operator. PHP example (rewriting in C++ should give huge performance boost I guess).

    0 讨论(0)
  • 2020-12-07 19:49

    Check Contrast Transfer Functions (CTF)

    Here's an implementation
    Here's an explanation

    0 讨论(0)
  • 2020-12-07 19:58

    As e.g. shown in this Matlab Central page, the sharpness can be estimated by the average gradient magnitude.

    I used this in Python as

    from PIL import Image
    import numpy as np
    
    im = Image.open(filename).convert('L') # to grayscale
    array = np.asarray(im, dtype=np.int32)
    
    gy, gx = np.gradient(array)
    gnorm = np.sqrt(gx**2 + gy**2)
    sharpness = np.average(gnorm)
    

    A similar number can be computed with the simpler numpy.diff instead of numpy.gradient. The resulting array sizes need to be adapted there:

    dx = np.diff(array)[1:,:] # remove the first row
    dy = np.diff(array, axis=0)[:,1:] # remove the first column
    dnorm = np.sqrt(dx**2 + dy**2)
    sharpness = np.average(dnorm)
    
    0 讨论(0)
提交回复
热议问题