SVLaursen / Python-RGB-to-HSI

A small Python algorithm made for a project at AAU. Converts an RGB image to the HSI spectrum.
MIT License
11 stars 3 forks source link

Adding Jit #1

Open 8bignic8 opened 3 years ago

8bignic8 commented 3 years ago

Hey I added Jit to your Programm but i dont know how to push to your projekt its much faster, soooo. Here is the code: requrements conda install numba

import cv2 import numpy as np import math from numba import jit

def RGB_TO_HSI(img):

with np.errstate(divide='ignore', invalid='ignore'):

    #Load image with 32 bit floats as variable type
    bgr = np.float32(img)/255

    #Separate color channels
    blue = bgr[:,:,0]
    green = bgr[:,:,1]
    red = bgr[:,:,2]

    #Calculate Intensity
    def calc_intensity(red, blue, green):
        return np.divide(blue + green + red, 3)

    #Calculate Saturation
    def calc_saturation(red, blue, green):
        minimum = np.minimum(np.minimum(red, green), blue)
        saturation = 1 - (3 / (red + green + blue + 0.001) * minimum)

        return saturation

    #Calculate Hue
    def calc_hue(red, blue, green):
        hue = np.copy(red)
        i = 0
        while (i <= int(blue.shape[0]) - 1):
            j = 0
            while (j <= int(blue.shape[1]) - 1):
                hue[i][j] = 0.5 * ((red[i][j] - green[i][j]) + (red[i][j] - blue[i][j])) / \
                            math.sqrt((red[i][j] - green[i][j]) ** 2 +
                                      ((red[i][j] - blue[i][j]) * (green[i][j] - blue[i][j])))
                hue[i][j] = math.acos(hue[i][j])

                if blue[i][j] <= green[i][j]:
                    hue[i][j] = hue[i][j]
                else:
                    hue[i][j] = ((360 * math.pi) / 180.0) - hue[i][j]
                j = j + 1
            i = i + 1

        return hue

        return hue

    #Merge channels into picture and return image
    jitHUE = jit()(calc_hue)
    hsi = cv2.merge((jitHUE(red, blue, green), calc_saturation(red, blue, green), calc_intensity(red, blue, green)))
    return hsi
amirshnll commented 2 years ago

@8bignic8

Your code has a divide by zero bug

---> hsi = cv2.merge((jitHUE(red, blue, green), calc_saturation(red, blue, green), calc_intensity(red, blue, green)))

ZeroDivisionError: division by zero

In solid black image

8bignic8 commented 2 years ago
hsi = cv2.merge(
     (jitHUE(
             red, blue, green), 
      calc_saturation(
              red, blue, green), 
      calc_intensity(
              red, blue, green)))

it is the same code as here but with jit. And a black image changed to hsi is still black or the I is thereby 0 so no information is passed anyway?

8bignic8 commented 2 years ago

If you can tell me where exactly the division by zero happens maybe I can help

amirshnll commented 2 years ago

If you can tell me where exactly the division by zero happens maybe I can help

Using photoshop or other graphical software, create a 20x20 image with a single black color. In base code in this repository, in this case you get nan but in your code we get the divide zero bug. As a result, your code runs extremely fast. This is an excellent point. I prefer that you handle this exception with try ... except sincerely