基于C++的OpenCV多视频拼接FPS过低问题及方法咨询
Hey there! Let's break down your issues step by step—first the frustrating low FPS problem, then whether cv2::Stitcher is suitable for multi-video stitching.
Your code has several critical inefficiencies that are dragging down performance:
Reinitializing Stitcher Every Frame
You’re creating a newStitcherinstance inside the while loop withStitcher stitcher = Stitcher::createDefault(true);. Initializing Stitcher involves setting up heavy components like feature detectors, matchers, and homography estimators—doing this every single frame wastes massive amounts of time. Move this line outside the loop so it runs once at the start.Redundant Frame Reads
You’re reading each frame twice: first withcap >> frame;then immediately withcap.read(frame);. This skips a frame each iteration and adds unnecessary I/O overhead. Pick one method (either>>orread()) and stick with it.Slow Resize Interpolation
INTER_CUBICis high-quality but computationally expensive. For real-time video processing, switch toINTER_LINEAR(balanced speed/quality) or evenINTER_NEAREST(fastest) if you can tolerate minor quality loss—this will speed up resizing significantly.Full Stitch Pipeline Every Frame
Thestitch()method runs the entire workflow: feature detection, matching, homography estimation, warping, and blending. For video, consecutive frames have minimal camera movement, so you don’t need to re-run the full pipeline every time. Reusing precomputed camera parameters after the first stitch will save tons of processing power.
cv2::Stitcher::stitch Be Used for Multi-Video Stitching? Short answer: Yes, but not the way you’re using it. OpenCV’s Stitcher is designed primarily for image stitching, but you can adapt it for video—you just need to avoid running the full stitching pipeline on every frame.
Here’s the right approach:
- Capture the first frame from each video and run
stitch()once to compute camera extrinsic parameters (homographies) and initialize the stitcher’s state. - For subsequent frames, reuse these precomputed parameters to only perform warping and blending (skip feature detection/matching unless camera movement is drastic).
- If your cameras are fixed (no movement), pre-calibrate homographies once using static images and apply them directly to every frame—this will give you the highest possible FPS.
Here’s a revised version of your code with all the fixes applied:
#include <opencv2/opencv.hpp> #include <iostream> using namespace cv; using namespace std; int main() { VideoCapture cap("video1.mp4"), cap2("video2.mp4"), cap3("video3.mp4"); if (!cap.isOpened() || !cap2.isOpened() || !cap3.isOpened()) { cerr << "Failed to open video files!" << endl; return -1; } // Initialize stitcher ONCE outside the loop Ptr<Stitcher> stitcher = Stitcher::createDefault(true); Stitcher::Status stitchStatus; Mat panorama; // Capture initial frames for first-time stitching (to set up parameters) Mat frame, frame2, frame3; cap.read(frame); cap2.read(frame2); cap3.read(frame3); // Resize with faster interpolation resize(frame, frame, Size(320, 240), 0, 0, INTER_LINEAR); resize(frame2, frame2, Size(320, 240), 0, 0, INTER_LINEAR); resize(frame3, frame3, Size(320, 240), 0, 0, INTER_LINEAR); vector<Mat> initialFrames = {frame, frame2, frame3}; stitchStatus = stitcher->stitch(initialFrames, panorama); if (stitchStatus != Stitcher::OK) { cerr << "Initial stitching failed! Error code: " << stitchStatus << endl; return -1; } // Process remaining frames while (true) { bool ret1 = cap.read(frame); bool ret2 = cap2.read(frame2); bool ret3 = cap3.read(frame3); if (!ret1 || !ret2 || !ret3) break; // Resize frames quickly resize(frame, frame, Size(320, 240), 0, 0, INTER_LINEAR); resize(frame2, frame2, Size(320, 240), 0, 0, INTER_LINEAR); resize(frame3, frame3, Size(320, 240), 0, 0, INTER_LINEAR); vector<Mat> currentFrames = {frame, frame2, frame3}; // Stitch using precomputed parameters (faster than full pipeline) stitchStatus = stitcher->stitch(currentFrames, panorama); if (stitchStatus != Stitcher::OK) { cerr << "Stitching failed in loop! Error code: " << stitchStatus << endl; continue; } imshow("Panorama", panorama); if (waitKey(1) == 27) break; // Exit on ESC key } // Cleanup cap.release(); cap2.release(); cap3.release(); destroyAllWindows(); return 0; }
- GPU Acceleration: Build OpenCV with CUDA support if you have an NVIDIA GPU—Stitcher has CUDA-accelerated backends that can drastically speed up feature detection and matching.
- Downscale Further: If you need even more speed, try resizing frames to 160x120 for stitching (you can upscale the final panorama if needed).
- Skip Frames: If your videos have high FPS, process every 2nd or 3rd frame instead of all frames to reduce workload.
内容的提问来源于stack exchange,提问作者pingxiu

