[Numpy-discussion] is there a faster way to get a buffer interface than ndarray.tostring()?

Chris Colbert sccolbert at gmail.com
Wed Feb 25 01:50:18 EST 2009


thanks!

On Wed, Feb 25, 2009 at 1:22 AM, Andrew Straw <strawman at astraw.com> wrote:

> Given what you're doing, may I also suggest having a look at
> http://code.astraw.com/projects/motmot/wxglvideo.html
>
> -Andrew
>
> Chris Colbert wrote:
> > As an update for any future googlers:
> >
> > the problem was with revpixels = pixeldata[::-1,:,;:-1] which apparently
> > returns an array that is discontinuous in memory. What Lisandro
> > suggested worked. pixeldata[::-1,:,;:-1].copy() returns a continuous
> > array object which natively implements a single-segment buffer
> > interface. i.e. no buffer(revpixels) is needed; just simply revpixels.
> >
> > array.copy() is also 50% faster than array.tostring() on my machine.
> >
> > Chris
> >
> > On Tue, Feb 24, 2009 at 9:27 PM, Chris Colbert <sccolbert at gmail.com
> > <mailto:sccolbert at gmail.com>> wrote:
> >
> >     thanks for both answers!
> >
> >
> >     Lisandro, you're right, I should have declared the array outside the
> >     loop. Thanks for catching that!
> >
> >     Robert, as always, thanks for the answer. Quick and to the point!
> >     You've helped me more than once on the enthought list :)
> >
> >
> >
> >     On Tue, Feb 24, 2009 at 8:06 PM, Lisandro Dalcin <dalcinl at gmail.com
> >     <mailto:dalcinl at gmail.com>> wrote:
> >
> >         When you do pixeldata[::-1,:,::-1], you just got a new array with
> >         different strides, but now non-contiguous... So I believe you
> really
> >         need a fresh copy of the data... tostring() copies, but could be
> >         slow... try to use
> >
> >         revpixels = pixeldata[::-1,:,::-1].copy()
> >
> >         ...
> >
> >         rgbBMP = wx.BitmapFromBuffer(640, 480, buffer(revpixels))
> >
> >
> >         Perhaps you could optimize this by declaring revpixels outside de
> >         loop, and then inside de loop doing
> >
> >         revpixels[...] = pixeldata[::-1,:,::-1]
> >
> >
> >         This way you will save the mem allocation of revpixels at each
> >         step of the loop.
> >
> >
> >
> >
> >
> >         On Tue, Feb 24, 2009 at 9:15 PM, Chris Colbert
> >         <sccolbert at gmail.com <mailto:sccolbert at gmail.com>> wrote:
> >         > Hi all,
> >         >
> >         >  I'm new to mailing list and relatively new (~1 year) to
> >         python/numpy. I
> >         > would appreciate any insight any of you may have here. The
> >         last 8 hours of
> >         > digging through the docs has left me, finally, stuck.
> >         >
> >         > I am making a wxPython program that includes webcam
> >         functionality. The
> >         > script below just brings up a simple display window that shows
> >         the webcam
> >         > feed. The problem I am running into is in the
> >         WebCamWorker.run() method.
> >         > This method reads the raw pixel data (in string form) from the
> >         webcam
> >         > buffer. This data (thank you microsoft!) comes in BGR and
> >         bottom-to-top. I
> >         > feed this buffer to the array constructor and then swap the
> >         pixel order to
> >         > RGB and top-to-bottom. This all happens very fast, ~1ms on a
> >         Quad Core, and
> >         > the majority of that time is spent constructing the array (the
> >         numpy pixel
> >         > swapping is on the order of E-5s !). The tostring() method,
> >         however, takes a
> >         > whopping 10ms to execute. Unfortunately, the
> >         wx.BitmapFromBuffer needs a
> >         > single segment buffer interface as an argument. Is there a way
> >         to expose my
> >         > numpy array as a buffer to cut down on this conversion time?
> >         >
> >         > I have tried sending the array to the PIL Image.fromarray(),
> >         but that
> >         > eventually requires me to do a Image.tostring() anyway, which
> >         negates any
> >         > benefit.
> >         >
> >         > Thanks in advance for the help!
> >         >
> >         > S. Chris Colbert
> >         > Rehabilitation Robotics Laboratory
> >         > University of South Florida
> >         >
> >         >
> >         > ####  Code #######
> >         >
> >         > import VideoCapture
> >         > import wx
> >         > import time
> >         > import threading
> >         > import numpy as np
> >         > import Image
> >         >
> >         >
> >         > class WebCamWorker(threading.Thread):
> >         >     _abort = 0
> >         >
> >         >     def __init__(self, parent):
> >         >         super(WebCamWorker, self).__init__()
> >         >
> >         >         self._parent = parent
> >         >         self.panel = wx.Panel(parent)
> >         >
> >         >     def run(self):
> >         >
> >         >         while not self._abort:
> >         >
> >         >             #numpy arrays reverse pixel data that comes in
> >         from CCD as BGR
> >         > and bottom to top
> >         >
> >         >             pixeldata = np.ndarray((480,640,3),
> >         > buffer=webcam.getBuffer()[0], dtype='u1')
> >         >             revpixels = pixeldata[::-1,:,::-1].tostring()
> >         #tostring is
> >         > an order of magnitude slower than the entire array
> >         manipulation. need a
> >         > faster method.
> >         >
> >         >             rgbBMP = wx.BitmapFromBuffer(640, 480, revpixels)
> >         >             dc = wx.ClientDC(self.panel)
> >         >             dc.DrawBitmap(rgbBMP, 0, 0)
> >         >             #b = time.clock()
> >         >             #print b-a
> >         >             time.sleep(0.015)
> >         >
> >         >
> >         >         return
> >         >
> >         >
> >         >
> >         > class TestWxWebCam(wx.Frame):
> >         >     def __init__(self, parent):
> >         >         wx.Frame.__init__(self, parent, -1, size=(640,480))
> >         >
> >         >         self.worker = WebCamWorker(self)
> >         >         self.worker.start()
> >         >
> >         >
> >         >
> >         > class TestApp(wx.App):
> >         >     def OnInit(self):
> >         >         self.frame = TestWxWebCam(None)
> >         >         self.frame.Show()
> >         >
> >         >         return True
> >         >
> >         >     def OnExit(self):
> >         >         WebCamWorker._abort = 1 #this is a hack
> >         >
> >         >
> >         > if __name__ == '__main__':
> >         >     webcam = VideoCapture.Device()
> >         >     webcam.setResolution(640, 480)
> >         >     webcam.displayCapturePinProperties()
> >         >     app = TestApp()
> >         >     app.MainLoop()
> >         >     del webcam
> >         >
> >         >
> >         > ### /Code ######
> >         >
> >         > _______________________________________________
> >         > Numpy-discussion mailing list
> >         > Numpy-discussion at scipy.org <mailto:Numpy-discussion at scipy.org>
> >         > http://projects.scipy.org/mailman/listinfo/numpy-discussion
> >         >
> >         >
> >
> >
> >
> >         --
> >         Lisandro Dalcín
> >         ---------------
> >         Centro Internacional de Métodos Computacionales en Ingeniería
> >         (CIMEC)
> >         Instituto de Desarrollo Tecnológico para la Industria Química
> >         (INTEC)
> >         Consejo Nacional de Investigaciones Científicas y Técnicas
> (CONICET)
> >         PTLC - Güemes 3450, (3000) Santa Fe, Argentina
> >         Tel/Fax: +54-(0)342-451.1594
> >         _______________________________________________
> >         Numpy-discussion mailing list
> >         Numpy-discussion at scipy.org <mailto:Numpy-discussion at scipy.org>
> >         http://projects.scipy.org/mailman/listinfo/numpy-discussion
> >
> >
> >
> >
> > ------------------------------------------------------------------------
> >
> > _______________________________________________
> > Numpy-discussion mailing list
> > Numpy-discussion at scipy.org
> > http://projects.scipy.org/mailman/listinfo/numpy-discussion
>
> _______________________________________________
> Numpy-discussion mailing list
> Numpy-discussion at scipy.org
> http://projects.scipy.org/mailman/listinfo/numpy-discussion
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/numpy-discussion/attachments/20090225/1843c34a/attachment.html>


More information about the NumPy-Discussion mailing list