2

I am trying to read the frames using imageio API. I have a reader as an object which I have received using imageio.get_reader(video_path,"ffmpeg")

nframes =int(reader.get_length())     
for ii in range(nframes):
    while frame_q.qsize() > 500: # so that we dont use huge amounts of memory
        time.sleep(1)
    cur_img = reader.get_next_data()
    frame_q.put(cur_img)
    #shape = cur_img.shape
    #noisy_img = np.uint8(cur_img.astype(np.float) + np.random.randn(*shape) * 20)
    #frame_q.put(noisy_img)
    if ii % 100 == 0:
        print("%i / %i frames in queue" % (ii, nframes))
print("All %i frames in queue" % (nframes))

Traceback:

 Traceback (most recent call last):
  File "/home/prashantb/anaconda3/envs/demo/lib/python3.6/multiprocessing/process.py", line 258, in _bootstrap
    self.run()
  File "/home/prashantb/anaconda3/envs/demo/lib/python3.6/multiprocessing/process.py", line 93, in run
    self._target(*self._args, **self._kwargs)
  File "multiprocess_detect_actions.py", line 61, in read_frames
    nframes =int(reader.get_length())
OverflowError: cannot convert float infinity to integer

Initially, the nframe was a float value then I tried to convert it into an integer but then I am getting an OverflowError.I will appreciate your advice on this. Thank you.

Sam
  • 352
  • 2
  • 4
  • 22
  • What is `reader`? Seems like it can be a generator with initially unknown length (presumably returning `inf` implies unknown, not infinite length, or you're going to be waiting a long time on infinite work). Knowing the API would be necessary to figure out how to handle the unknown/infinite reported length (Does `get_next_data` raise an exception when it runs out of data? Return a sentinel value? Something else?). – ShadowRanger Feb 20 '19 at 03:09
  • Is `reader` an instance of a class you've written? If so, you should figure out why its `get_length` method is returning infinity and fix that. If it comes from a library you're using, then you should check its API documentation to see what it means when it says it has an infinite length. Does it perhaps have an iterator-protocol API you could use insetead of `get_length()` and `get_next_data()`? If so, then `enumerate` could be your friend: `for ii, cur_img in enumerate(reader): #or enumerate(reader.something())` – Blckknght Feb 20 '19 at 03:09
  • @ShadowRanger reader is an object coming from imageio.get_reader() . get_next_data is not raising any exception. and also no sentinel value. – Sam Feb 20 '19 at 05:04

2 Answers2

4

According to the new 2019 update 2.5.0 version from imageio : "The reader of the ffmpeg plugin now always reports inf as the number of frames. Use reader.count_frames() to get the actual number, or estimate it from the fps and duration in the meta data." imageio update

Sam
  • 352
  • 2
  • 4
  • 22
1

In Python, float type can be infinity. To fixe your bug, you check if the value is inf ou -inf before convert to int:

def float_to_int(x):
    if x == float('inf') or x == float('-inf'):
        return float('nan') # or a large value you choose
    return int(x)

As @ShadowRanger noted, this solution just prevent the OverflowError error. You should investigate on the reader to fix the problem of infinite float.

Vincent
  • 472
  • 2
  • 8
  • Given that they turn around and plug this into `range`, you're just postponing the error by a line. There is a fundamental flaw with trying to do infinite work; odds are they're misusing their API. – ShadowRanger Feb 20 '19 at 03:07