Reputation: 9407
I am using this routine to get all frames of a video into an array of frames:
On Click:
private int CompareTwoVideos(string _firstVideoPath, string _secondVideoPath)
{
Capture _capture;
List<Image<Gray, Byte>> FirstALLFrames = new List<Image<Gray, Byte>>();
// ..
_capture = new Capture(FirstVideoLocation);
// get all frames
FirstALLFrames = GetAllFrames(_capture);
// do some image processing
// ..
_capture.Dispose();
return 0;
}
Utility Function:
List<Image<Gray, byte>> GetAllFrames(Capture _capture)
{
List<Image<Gray, byte>> AllFrames = new List<Image<Gray, byte>>();
int FramesCount = 0;
try
{
FramesCount = (int)_capture.GetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_FRAME_COUNT);
for (int i = 0; i < FramesCount - 1; i++)
{
AllFrames.Add(_capture.QueryGrayFrame().Resize(ImageWidth, ImageHeight, Emgu.CV.CvEnum.INTER.CV_INTER_LINEAR));
}
}
catch (Exception ex)
{
// Error pops here
}
return AllFrames;
}
On the first click everything works fine.
However, the error pops on the second click.
Any idea?
Upvotes: 1
Views: 160
Reputation: 1396
I am not a 100% sure what you mean with "second click" but I am assuming this means you run the code directly again to process another video.
It seems that your list simply becomes to big and takes up to much memory (which is also written under Exceptions in the List(T) MSDN documentation). You do dispose your _capture
object, but you don't dispose your list. Therefore there may still be references on the list which prevents it from properly being disposed and collected by the system (so make sure you don't have any other references to the list).
Also, replacing the reference (with your new List()
instance) will not release the collection right away and it take time before the garbage collector disposes the object. It's very likely that the second click then simply leads to your program using too much memory, since it now contains too whole videos in memory. Have you monitored your application memory usage?
You could therefore try a couple of things:
Use List.Clear()
method which may help, since it eliminates the values within the list. It does not directly free up allocated memory though. This could help since the garbage collection can quickly clean up the list, although I am unsure how effective this will be in your case.
Make sure all references to the list are eliminated by calling List = null
. Then force the garbage collector to collect the garbage directly by calling GC.Collect()
. This will take up resources, since you call the collector at a moment it may not be perfectly suitable, but especially if performance is not an issue this should not pose a problem.
Lastly, try to process each frame and directly discard it before processing the next frame. Or try to process the video in batches (whatever is possible). This will put less of a burden on your memory.
Upvotes: 1