I need to be able to compare two images and extract any unique pixels to create a third image. To accomplish this I did the following:
import cv2
import numpy as np
img = cv2.imread("old.jpg")
img2 = cv2.imread("new.jpg")
image2 = cv2.cvtColor(img2, cv2.COLOR_RGB2RGBA)
for (x,y,z), value in np.ndenumerate(img):
dif = img[x,y,0] == img2[x,y,0] #only checking one color for speed
diff = str(dif)
if "True" in diff:
image2[x,y,3] = 0
cv2.imwrite("result.png", image2)
This worked fairly well but the it took around 10 seconds for a 640 x 480 picture and I was hoping to get it closer to about half that time. So I changed this line:
dif = img[x,y,0] == img2[x,y,0]
to
dif = np.in1d(img[x,y,0], img2[x,y,0])
The results are identical but instead of speeding things up it now takes about 3 minutes. I'm at a complete loss as to why.
I realize that iterating over elements in large arrays is going to be time consuming in python but why is in1d so much slower?
(As a side note I would just use the "palette method" but I couldn't see a way to implement it for this purpose due to my limited knowledge of numpy arrays.)
np.in1d
checks each element of its first argument against each element of its second element in the worse case. For each element i,j
in img
it checks if there is an element k,l
in img2
with the same value. Meaning that for your 640x480
image you can end up doing (640x480)^2
comparisons.
On the other hand, ==
checks only elementwise, it checks if element i,j
of img
is equals to element i,j
of img2
. It will always has 640x480
comparisons.
np.in1d
will work if you have images of different sizes, ==
will work only for images of the same size.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With