【opencv】教程代码 —videoio(3)读取输入的视频文件,提取出R、G或B颜色通道,并将结果写入新的视频文件...

cpp 复制代码
#include <iostream>  // 引入标准输入输出流库,用于输入输出
#include <string>   // 引入字符串库


#include <opencv2/core.hpp>     // 引入OpenCV基础结构(cv::Mat等)
#include <opencv2/videoio.hpp>  // 引入OpenCV视频读写


using namespace std; // 使用标准命名空间std
using namespace cv;  // 使用OpenCV命名空间cv


// 帮助函数,用于显示程序的使用说明
static void help()
{
    cout
        << "------------------------------------------------------------------------------" << endl
        << "This program shows how to write video files."                                   << endl
        << "You can extract the R or G or B color channel of the input video."              << endl
        << "Usage:"                                                                         << endl
        << "./video-write <input_video_name> [ R | G | B] [Y | N]"                          << endl
        << "------------------------------------------------------------------------------" << endl
        << endl;
}


// 主函数入口
int main(int argc, char *argv[])
{
    help(); // 调用帮助函数


    // 检查参数数量是否正确
    if (argc != 4)
    {
        cout << "Not enough parameters" << endl;
        return -1;
    }


    const string source      = argv[1];           // 命令行参数1:输入视频文件名
    const bool askOutputType = argv[3][0] =='Y';  // 命令行参数3:是否询问输出视频的类型(编码格式)


    VideoCapture inputVideo(source);              // 打开输入视频
    if (!inputVideo.isOpened())
    {
        cout  << "Could not open the input video: " << source << endl;
        return -1;
    }


    // 查找视频文件名中的扩展名位置
    string::size_type pAt = source.find_last_of('.');                  
    const string NAME = source.substr(0, pAt) + argv[2][0] + ".mp4";  //avi 生成新的视频文件名


    // 获取输入视频的编码格式
    int ex = static_cast<int>(inputVideo.get(CAP_PROP_FOURCC));     


    // 通过位运算将编码格式从int转换成字符形式
    char EXT[] = {(char)(ex & 0XFF) , (char)((ex & 0XFF00) >> 8),(char)((ex & 0XFF0000) >> 16),(char)((ex & 0XFF000000) >> 24), 0};


    // 获取输入视频的尺寸
    Size S = Size((int) inputVideo.get(CAP_PROP_FRAME_WIDTH),    // 宽
                  (int) inputVideo.get(CAP_PROP_FRAME_HEIGHT));  // 高


    VideoWriter outputVideo;                                    // 创建视频写入对象
    if (askOutputType)
        outputVideo.open(NAME, ex=-1, inputVideo.get(CAP_PROP_FPS), S, true);
    else
        outputVideo.open(NAME, ex, inputVideo.get(CAP_PROP_FPS), S, true);


    // 打开输出视频
    if (!outputVideo.isOpened())
    {
        cout  << "Could not open the output video for write: " << source << endl;
        return -1;
    }


    // 显示输入视频的相关信息
    cout << "Input frame resolution: Width=" << S.width << "  Height=" << S.height
         << " of nr#: " << inputVideo.get(CAP_PROP_FRAME_COUNT) << endl;
    cout << "Input codec type: " << EXT << endl;


    // 选择要保存的颜色通道
    int channel = 2; // 默认选择蓝色通道
    switch(argv[2][0])
    {
      case 'R' : channel = 2; break;
      case 'G' : channel = 1; break;
      case 'B' : channel = 0; break;
    }
    
    // 创建相关的Mat对象
    Mat src, res;
    vector<Mat> spl;


    // 无限循环,直到视频读取完毕
    for(;;)
    {
        inputVideo >> src;              // 读取视频帧
        if (src.empty()) break;         // 如果读取到空帧,则停止


        split(src, spl);                // 处理视频帧,分离色彩通道
        for (int i =0; i < 3; ++i)
            if (i != channel)
                spl[i] = Mat::zeros(S, spl[0].type()); // 将非选定通道置零
        merge(spl, res); // 合并通道


        outputVideo << res; // 将处理后的帧写入输出视频
    }


    cout << "Finished writing" << endl; // 写入完成
    return 0;
}

这段代码是一个C++程序,使用OpenCV库来处理视频文件。具体功能如下:

  1. 程序读取一个输入视频,并允许用户选择摘取红(R)、绿(G)或蓝(B)色彩通道。

  2. 用户可以选择是否询问输出视频的编码格式

  3. 如果输入视频成功打开,程序会通过用户选择提取特定的颜色通道,并将这些帧写入到一个新的视频文件中。

  4. 程序最终输出一个只包含选定颜色通道的视频文件。

char EXT[] = {(char)(ex & 0XFF) , (char)((ex & 0XFF00) >> 8),(char)((ex & 0XFF0000) >> 16),(char)((ex & 0XFF000000) >> 24), 0};

outputVideo.open(NAME, ex=-1, inputVideo.get(CAP_PROP_FPS), S, true);

./test.exe baseDraw.mp4 R Y 运行示例

报错:[ERROR:0@1.220] global cap.cpp:645 cv::VideoWriter::open VIDEOIO(CV_IMAGES): raised OpenCV exception:

split(src, spl);

Mat::zeros(S, spl[0].type())

merge(spl, res);

相关推荐
Ronin-Lotus2 小时前
深度学习篇---剪裁&缩放
图像处理·人工智能·缩放·剪裁
cpsvps3 小时前
3D芯片香港集成:技术突破与产业机遇全景分析
人工智能·3d
国科安芯3 小时前
抗辐照芯片在低轨卫星星座CAN总线通讯及供电系统的应用探讨
运维·网络·人工智能·单片机·自动化
AKAMAI4 小时前
利用DataStream和TrafficPeak实现大数据可观察性
人工智能·云原生·云计算
Ai墨芯1114 小时前
深度学习水论文:特征提取
人工智能·深度学习
无名工程师4 小时前
神经网络知识讨论
人工智能·神经网络
nbsaas-boot4 小时前
AI时代,我们更需要自己的开发方式与平台
人工智能
SHIPKING3934 小时前
【机器学习&深度学习】LLamaFactory微调效果与vllm部署效果不一致如何解决
人工智能·深度学习·机器学习
jonyleek5 小时前
如何搭建一套安全的,企业级本地AI专属知识库系统?从安装系统到构建知识体系,全流程!
人工智能·安全
MQ_SOFTWARE6 小时前
AI驱动的金融推理:Fin-R1模型如何重塑行业决策逻辑
人工智能·金融