讲师中心 微信公众号
AI工具推荐 视频效率加速

C++如何调用FFmpeg处理音视频?(libavcodec集成)

梦枫大大_6499

梦枫大大_6499

发布时间:2026-02-21 10:55:57

|

369人浏览过

|

来源于php中文网

原创

avcodec_open2返回负值主因是AVCodecContext未用avcodec_alloc_context3分配、未调avcodec_parameters_to_context填充参数、或解码器与上下文不匹配。

c++如何调用ffmpeg处理音视频?(libavcodec集成)

ffmpeg解码失败:avcodec_open2返回负数

多数人卡在这一步,不是代码写错,是没初始化或上下文没配对。avcodec_open2 返回负值(比如 -22)基本等于“参数不合法”,常见原因有三个:

  • AVCodecContext 没用 avcodec_alloc_context3 分配,而是手动生成结构体——C++里容易误用 new AVCodecContext,但 FFmpeg 内部依赖其内存布局和默认值
  • 调用前漏了 avcodec_parameters_to_context(从 AVStream 拿参数填进 context),尤其在封装格式(如 MP4)中,codecpar 和 codec 是分离的
  • 传入的 AVCodec* 和 AVCodecContext 不匹配,比如用 avcodec_find_decoder(AV_CODEC_ID_H264) 找到解码器,却往 context 里硬塞了 AAC 的参数

实操建议:先确认 avcodec_find_decoder 返回非空,再用 avcodec_parameters_to_context(ctx, stream->codecpar) 填充,最后才调 avcodec_open2。

C++里怎么安全释放AVFrame和AVPacket

FFmpeg 的内存管理是“谁分配、谁释放”原则,但 C++ 容易误用 delete 或忘记释放导致崩溃或内存泄漏。关键点在于:av_frame_alloc / av_packet_alloc 分配的对象,必须用 av_frame_free / av_packet_unref(不是 free,也不是 delete)。

  • AVFrame:用 av_frame_alloc() 创建后,每帧处理完必须调 av_frame_free(&frame);如果只是借用(比如从解码器拿到的输出帧),不能 free,应改用 av_frame_unref 清空引用计数
  • AVPacket:av_packet_alloc() 后用 av_packet_unref() 释放数据缓冲区;若用 av_packet_move_ref() 转移所有权,则原 packet 自动变为空,无需再 unref
  • RAII 封装可行但需谨慎:FFmpeg 内部可能重用 buffer,直接在析构里 av_frame_free 没问题,但别在拷贝构造里做浅拷贝——AVFrame 不支持深拷贝,要用 av_frame_clone

libavcodec硬解(NVDEC/QSV)启用失败

想用 GPU 解码却 fallback 到 CPU,大概率是没设对 AVCodecContext 的 hw_device_ctx 或没选对 codec。

C++14
C++14

C++14 对 C++11 的修正与增强版本,适合旧系统维护和较老工具链兼容。

下载

立即学习“C++免费学习笔记(深入)”;

  • 必须先调 av_hwdevice_ctx_create 创建设备上下文(比如 AV_HWDEVICE_TYPE_CUDA),再把返回的 AVBufferRef* 赋给 ctx->hw_device_ctx
  • 解码器必须显式选择硬件加速类型:比如 H.264,要找 avcodec_find_decoder_by_name("h264_cuvid")(NVIDIA)或 "h264_qsv"(Intel),不能只用 avcodec_find_decoder(AV_CODEC_ID_H264)
  • 硬解成功后,avcodec_receive_frame 返回的 AVFrame 的 format 是 AV_PIX_FMT_CUDA 等硬件格式,不能直接用 OpenCV 显示,得先用 av_hwframe_transfer_data 拷贝到系统内存

注意:Windows 上 NVDEC 需要驱动支持(≥ 418.x),Linux 上 CUDA 设备需可访问(nvidia-smi 能看到),否则 av_hwdevice_ctx_create 直接返回负值。

avcodec_send_packet后avcodec_receive_frame一直返回EAGAIN

这不是卡死,是 FFmpeg 的流式解码模型正常行为:输入 packet 不够触发一帧输出,或者还没收到关键帧(如 H.264 的 IDR 帧)。典型场景是读取网络流或不完整文件头时。

  • 确保至少送入一个含关键帧的 AVPacket(pkt.flags & AV_PKT_FLAG_KEY),否则解码器会等
  • 送完所有 packet 后,必须再调一次 avcodec_send_packet(nullptr) 告诉解码器“输入结束了”,否则内部缓存不 flush,receive_frame 永远不会吐出剩余帧
  • 不要在循环里无条件反复调 receive_frame,应配合 send_packet 的返回值判断:只有 send_packet 成功后,才值得多试几次 receive_frame;连续返回 EAGAIN 且没新 packet 可送,说明真没数据了

硬解下还可能因 GPU buffer 满而阻塞,这时 receive_frame 也会返回 EAGAIN,但通常伴随 av_hwframe_get_buffer 失败,需要检查设备上下文状态。

热门AI工具

更多
UP简历
UP简历 Hot

一款AI办公效率工具,主要用于基于AI技术的免费在线简历制作工具,适合需要提升相关任务效率的用户。

WorkBuddy

一款AI办公效率工具,主要用于腾讯云推出的AI原生桌面智能体工作台,适合需要提升相关任务效率的用户。

超级简历WonderCV

一款AI办公效率工具,主要用于免费求职简历模版下载制作,应届生职场人必备简历制作神器,适合需要提升相关任务效率的用户。

Laper
Laper Hot

Laper是专为编剧、导演和制片人推出的 AI 原生剧本创作工具。

Flowith
Flowith Hot

Flowith是一款基于画布和智能体工作流的 AI 协作工作空间。

豆包大模型

豆包大模型是一款由字节跳动推出的企业级大语言模型服务平台。

花生AI
花生AI Hot

一款AI视频创作工具,主要用于B站推出的AI视频创作工具,适合需要提升相关任务效率的用户。

DeepSeek

DeepSeek是一款面向对话、写作、编程和推理场景的AI大模型工具。

Loomy
Loomy Hot

一款AI工具,主要用于科大讯飞发布的桌面级 AI 助理,比 OpenClaw 更易用、更安全!,适合需要提升相关任务效率的用户。

相关专题

更多
format在python中的用法
format在python中的用法

Python中的format是一种字符串格式化方法,用于将变量或值插入到字符串中的占位符位置。通过format方法,我们可以动态地构建字符串,使其包含不同值。php中文网给大家带来了相关的教程以及文章,欢迎大家前来阅读学习。

1809

2023.07.31

python中的format是什么意思
python中的format是什么意思

python中的format是一种字符串格式化方法,用于将变量或值插入到字符串中的占位符位置。通过format方法,我们可以动态地构建字符串,使其包含不同值。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

1211

2024.06.27

golang结构体相关大全
golang结构体相关大全

本专题整合了golang结构体相关大全,想了解更多内容,请阅读专题下面的文章。

5174

2025.06.09

golang结构体方法
golang结构体方法

本专题整合了golang结构体相关内容,请阅读专题下面的文章了解更多。

5331

2025.07.04

数据库Delete用法
数据库Delete用法

数据库Delete用法:1、删除单条记录;2、删除多条记录;3、删除所有记录;4、删除特定条件的记录。更多关于数据库Delete的内容,大家可以访问下面的文章。

3371

2023.11.13

drop和delete的区别
drop和delete的区别

drop和delete的区别:1、功能与用途;2、操作对象;3、可逆性;4、空间释放;5、执行速度与效率;6、与其他命令的交互;7、影响的持久性;8、语法和执行;9、触发器与约束;10、事务处理。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

1025

2023.12.29

windows查看端口占用情况
windows查看端口占用情况

Windows端口可以认为是计算机与外界通讯交流的出入口。逻辑意义上的端口一般是指TCP/IP协议中的端口,端口号的范围从0到65535,比如用于浏览网页服务的80端口,用于FTP服务的21端口等等。怎么查看windows端口占用情况呢?php中文网给大家带来了相关的教程以及文章,欢迎大家前来阅读学习。

3399

2023.07.26

查看端口占用情况windows
查看端口占用情况windows

端口占用是指与端口关联的软件占用端口而使得其他应用程序无法使用这些端口,端口占用问题是计算机系统编程领域的一个常见问题,端口占用的根本原因可能是操作系统的一些错误,服务器也可能会出现端口占用问题。php中文网给大家带来了相关的教程以及文章,欢迎大家前来学习阅读。

2938

2023.07.27

Docker Desktop怎么设置端口映射
Docker Desktop怎么设置端口映射

本专题聚焦Docker Desktop容器端口映射与访问配置,整理从创建容器、设置端口绑定到验证本地服务访问的操作流程。针对端口被占用、映射配置错误、容器服务无法访问等情况,也提供相应的检查方向,方便用户完成端口配置。

0

2026.11.03

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
C++ Core Guidelines
C++ Core Guidelines

共0课时 | 0人学习

C++ Reference
C++ Reference

共0课时 | 0人学习

C++ 官方标准说明
C++ 官方标准说明

共0课时 | 0人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn