Machine Vision

cancel
Showing results for 
Search instead for 
Did you mean: 

Do PixelValue2D properties return a new array, or a reference?

I'm writing a program to acquire data from an IMAQ device to a ring buffer, and operate on the data from there. I'm extracting a PixelValue2D, and I'm curious about how it works.

 

I want to access the data as a short[,], so I write:

 

PixelValue2D pixVal = _session.Acquisition.Extract(bufferNumber, out bufferNumber).ToPixelArray();

short[,] imgData = pixVal.I16;

 

Does the pixVal.I16 return a reference to the data, or a new copy of the data? This information will be very helpful for keeping my program as efficient as possible.

 

Thanks!

0 Kudos
Message 1 of 16
(5,070 Views)

Hi middletongard,

 

Could you tell me which language you are working in so that I may be of better assistance?  I have not been able to find a reference to this function.

 

Lynn

National Instruments
Senior Systems Engineer
0 Kudos
Message 2 of 16
(5,042 Views)

C#

 

Thanks

0 Kudos
Message 3 of 16
(5,041 Views)

I found information for PixelValue2D.I16 here within the Visual Studio 2008 help:

 

ms-help://MS.VSCC.v90/MS.VSIPCC.v90/NI.MeasurementStudio.2008/NINETVision/html/NationalInstruments.Vision.PixelValue2D.I16.html

PixelValue2D.I16 Property

Gets the pixel values for images of type I16.

[Visual Basic]
Public Property ReadOnly I16 As Short(,)
[C#]
public short[,] I16 {get;}

Property Value

The pixel values for images of type I16.

See Also

PixelValue2D Class | PixelValue2D Members | NationalInstruments.Vision Namespace

0 Kudos
Message 4 of 16
(5,040 Views)

Hey!

 

Ah yep, I found that right after you.  Well I'm glad you've got a solution. Best of luck with your application!

 

Regards,

 

Lynn

National Instruments
Senior Systems Engineer
0 Kudos
Message 5 of 16
(5,038 Views)

Ah, I don't have the solution quite yet - the information does not tell me whether a copy of the data is made, or a reference to the data is returned.

 

If this information is implied in the definition, I haven't caught it. Could you please find out and let me know explicitly whether a new copy of the data is made and returned, or it's simply a reference to the data in PixelData2D (no copy) that is returned?

 

Thanks

0 Kudos
Message 6 of 16
(5,036 Views)

Hi middletongard,

 

PixelArray.png

 

It appears as though the PixelValue2D is ImaqBuffer which a a zero-copy operation.

 

Lynn

National Instruments
Senior Systems Engineer
0 Kudos
Message 7 of 16
(5,016 Views)

Similar to middletongard, I'm trying to acquire IMAQ data in C# and extract the data into a short array for further processing. From the last post I see that extracting PixelValue2D from ImaqBuffer is a zero-copy operation, but I still wonder whether new memory is being allocated?

 

The reason I ask is that my application crashes with an OutOfMemoryException after running for a couple seconds.

 

This is the line of code that generates the exception:

short[,] data = mSession.Acquisition.Extract(BufferNumber, out CurrentBufferNumber).ToPixelArray().I16;

 

And this is the relevant part of the stack trace:

Exception Info: System.OutOfMemoryException

Stack:

   at NationalInstruments.Vision.Internal.Utilities.ConvertIntPtrFlatTo2DArrayInt16(IntPtr, Int32, Int32, Boolean)

   at NationalInstruments.Vision.VisionImage.ImageToArray(NationalInstruments.Vision.RectangleContour)

   at NationalInstruments.Vision.Acquisition.Imaq.Internal.ImaqVisionImageBuffer.ToPixelArray()

   at NationalInstruments.Vision.Acquisition.Imaq.ImaqBuffer.ToPixelArray()

 

Note that the exception is thrown from ToPixelArray(), not getting the I16 property. 

 

I would appreciate any help I can get!

0 Kudos
Message 8 of 16
(4,751 Views)

Accessing raw pixel data as an array out of a Vision image is always a copy operation. Otherwise there is no way to properly synchronize access between the Vision image's access to its internal data and the user's access via the array.

 

Eric

0 Kudos
Message 9 of 16
(4,748 Views)

Thanks for the quick response Eric, that definitely makes sense to me. But my issue is with the memory allocation rather than the copying. I would like to reuse memory instead of repeatedly allocating and freeing.

 

A desireable solution would be if I could pass in the destination array when extracting the data, i.e.:

//During initialization

   short[,] data = new short[xSize, ySize];

//Later, during acquisition

   mSession.Acquisition.Extract(...).ToPixelArray(out data);

 

I know that call doesn't exist, but I wonder if there is a workaround for it.

 

My application can't afford to run the garbage collector during acquisition, so the goal is to allocate buffers before the start of acquisition and then reuse them.

0 Kudos
Message 10 of 16
(4,744 Views)