[Numpy-discussion] "aligned" matrix / ctypes

Zachary Pincus zachary.pincus at yale.edu
Wed Apr 23 17:26:51 EDT 2008


Hi,

Thanks a ton for the advice, Robert! Taking an array slice (instead of  
trying to set up the strides, etc. myself) is a slick way of getting  
this result indeed.

>> I need to allocate a numpy array that I will then pass to a camera
>> driver (via ctypes) so that the driver can fill the array with  
>> pixels.
>> The catch is that the driver requires that rows of pixels start at 4-
>> byte boundaries.
>>
>> The sample C++ code given for allocating memory for this is (pixels
>> are unsigned shorts):
>>
>> // Two bytes for each pixel, then round
>> // up to the next multiple of four.
>> long width_bytes = ( ( 2 * width_pixels ) + 3 ) & -4;
>> long allocated_size = width_bytes * height;
>> unsigned char* image_data = new unsigned char[allocated_size];

> Note that the approach above doesn't ensure that the first row is
> correctly aligned. It just assumes that the allocator will always
> start a new block aligned at 4 bytes (which may be reasonable for the
> platforms you are targetting).

Hmm, good point. The SDK/example code is pretty flakey, so I bet they  
just make this assumption.

> To solve the initial alignment, you overallocate a 1D array by 3 bytes
> and find the offset from the allocated initial address which is
> correctly aligned.

Sorry -- I haven't had to ever concern myself with alignment before  
this, so I'm not sure how to go about this step. Do I just look at the  
raw pointer address and see what offset I need to give it to get it to  
be divisible by four?

> Slice out [:allocated_size] portion of this,
> .view() it as uint16, reshape it to
> (height,width_pixels+width_pixels%2), then slice out
> [:,:width_pixels].

Everything else makes good sense. Thanks again!

Zach




More information about the NumPy-Discussion mailing list