Whether or not this is possible depends on your container and codec being used. Assuming the codec allows retrieving the total number of frames, you can do something like this:
import imageio.v3 as iio
import numpy as np
my_video = "imageio:cockatoo.mp4"
props = iio.improps(my_video, plugin="pyav")
# Make sure the codec knows the number of frames
assert props.shape[0] != -1
for idx in np.linspace(0, props.shape[0]-1, 5, dtype=int):
    # imageIO < 2.21.0
    image = iio.imread(my_video, index=idx)
    # imageIO > 2.21.0
    # image = iio.imread(my_video, index=idx, plugin="pyav")
    iio.imwrite(f"delete_me/frame_{idx:03d}.png", image)
A few notes:
- you want to use pyav for the call to iio.improps, because it doesn't decode frames, so it is fast.
- some codecs or containers (especially when streaming video) either don't report or can't report the number of frames stored within. In this case props.shape[0]will be-1and we can't use this method.
- normally I'd recommend using pyav for the imreadcall as well, but there is a bug in the plugin that causes an EoF exception when trying toindex=to the last frame. This will be fixed by #855, though I can't say if it will make it into this weekly release or the next.
- if the codec used doesn't guarantee constant framerate, you won't get any speed advantages over iio.imiterbecause we can't safely predict how far into the video to seek. If you know that your video has a constant framerate, however, you can use theconstant_frameratekwarg of the pyav plugin to speed things up. (IMPORTANT: if the video has variable framerate and you set this anyway the seek will not be accurate.)
- As usual, you can use iio.imopenif you want to do all of these operations without reopening the video each time.