[Image-SIG] PIL vs Numpy in raster calculations

Chris Ps lubensch.proletariat.inc at gmail.com
Mon May 25 23:23:03 CEST 2009


Hi,
Lately I'm dealing with image statistics with PIL (1.1.6). After I've read
that numpy (1.2.1) is very fast, I've also tried this library to make the
same calculations. I noticed something I would like your opinion about since
I'm not an experienced user.
With a 2000x2000 RGB tif image (~11.0mb) I tried the following with PIL and
numpy:

from numpy import *
from PIL import Image,ImageStat

imga = Image.open("a.tif")
imgar = asarray(imga)

for i in range(1,3):
    stats = ImageStat.Stat(imga)
    stats.mean

for j in range(1,3):
    mean(imgar[:,:,0])
    mean(imgar[:,:,1])
    mean(imgar[:,:,2])

When I timed the for loops I discovered that PIL is about 50 times faster
than numpy!
Since I'm mostly interested in calculating statistics for sub-windows of the
original image I've also tried the same using the crop function from PIL.
This resluted in something like the following:

box = (10,10,20,20)
for i in range(1,1000):
    stats = ImageStat.Stat(imga.crop(box))
    stats.mean

box = imgar[10:21,10:21,:]
for i in range(1,1000):
    mean(box[:,:,0])
    mean(box[:,:,1])
    mean(box[:,:,2])

The thing is that this time numpy was about 10 times faster than PIL!
I figured that the crop function could be slow so I did the initial test,
only this time the image (a.tif) was reduced to 10x10 pixels. In this test
numpy still performed 80 times faster than PIL, so I guess tha crop is
rather fast. The situation changed again when I tried an image 100x100
pixels large. In this test PIL was 2 times faster than numpy.
After all these tests I conclude that the problem is when numpy has to
calculate the stats for large images. Probably mean() copies the image
before calculations take place so this copy action costs considerable time.
On the other hand when you have to deal with small sub-images of an original
large image, then this copy action is fast and the calculations with numpy
are performed extremely fast.
Is this the case? Is something wrong in the above code that I could avoid?
Thank you and sorry for the long post.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/image-sig/attachments/20090526/fb88594e/attachment.htm>


More information about the Image-SIG mailing list