在ffmpeg中,网络视频流h264为什么默认的转为YUV而不是其他格式

在做网络视频的时候,有些视频的编程概念,早点知道,早点弄清楚会少走很多的弯路。对应视频的转码,传输,一开始如果直接跟着代码跑的话,很容易觉得自己都明白了,但是为什么这样做,好像也讲出去个一二三来。

比如:在ffmpeg中,网络视频流h264为什么默认的转为YUV而不是其他格式?

从这个问题开始,我们慢慢的把一些概念理清楚,这样一来,编程的时候就容易理解了。

什么是h264

也被称为AVC(高级视频编码),是一种视频压缩标准。这是一种高效的视频编码方法,可以在保持高质量的同时,大幅度减少所需的带宽和存储空间。H264编码的视频可以在各种设备上播放,包括电视、电脑、智能手机等。在视频处理中,H264用于压缩视频数据,使其更便于传输和存储。

什么是YUV

这是一种颜色编码系统,常用于视频系统。YUV模型定义了一个颜色空间,其中Y表示亮度(灰度),而U和V表示色度(色彩和饱和度)。这种颜色编码方式的优点是可以更有效地压缩颜色信息,因为人眼对亮度的敏感度远高于色度。在视频处理中,YUV通常用于在保留视觉质量的同时减少所需的带宽或存储。

还有一个概念那就是我们经常提到的RGB格式。

什么是RGB

RGB是一种加色模型,其中R代表红色,G代表绿色,B代表蓝色。RGB模型采用红、绿、蓝三种颜色的光以不同的比例混合,以产生其他颜色。RGB模型主要用于显示设备,如电脑屏幕、电视和手机等,因为这些设备通过发射红、绿、蓝三种颜色的光来显示图像。RGB模型的优点是可以表示大范围的颜色,并且直观易于理解。

可以这么说RGB,YUV是不同时代的产物,一开始我们在设计黑白电视机的时候,只要有灰度就能显示图片,图片知识黑白的而已,到了彩色电视以后,又引入了U和V这两个向量,颜色的问题也就兼容了。

到了LED的时代,采用红、绿、蓝三种颜色的光以不同的比例混合,以产生其他颜色,也就是RGB。

为什么H264编码通常解码为YUV格式,而不是RGB格式的

H264编码的视频通常首先解码为YUV格式,而不是RGB格式,这主要是由于以下几个原因:

  1. 压缩效率:YUV格式的颜色编码更适合于视频压缩。在YUV格式中,亮度信息(Y)和色度信息(UV)是分开的,这使得在压缩过程中可以对色度信息进行更大程度的压缩,因为人眼对亮度的敏感度远高于色度。这就意味着,在相同的视频质量下,YUV格式的视频数据通常比RGB格式的视频数据更小。

  2. 兼容性:许多视频设备和系统,包括电视和DVD播放器等,都使用YUV格式。因此,解码为YUV格式可以确保视频在这些设备和系统上的兼容性。

  3. 色彩空间转换:虽然H264编码的视频可以被解码为RGB格式,但这通常需要额外的色彩空间转换步骤。相比之下,直接解码为YUV格式则更为简单和高效。

因此,虽然H264编码的视频可以被解码为RGB格式,但由于压缩效率、兼容性和处理效率的考虑,通常首先解码为YUV格式。

在视频的传输中用的是yuv还是h264

在视频的传输中,通常使用的是H264格式。这是因为H264是一种高效的视频压缩标准,它可以在保持高质量的同时,大幅度减少所需的带宽和存储空间。由于其高效的压缩性能,H264已经成为网络视频和流媒体的主流编码格式。

然而,这并不意味着YUV在视频传输中没有用处。实际上,YUV是一种颜色编码系统,用于在视频处理中有效地压缩颜色信息。在视频被编码为H264格式之前,通常会先将其转换为YUV格式。

因此,虽然在视频传输中主要使用H264格式,但YUV格式在视频处理和编码的过程中仍然起着重要的作用。

利用ffmpeg,把h264转为YUV

以下是一个使用FFmpeg库的基本示例,它展示了如何打开一个H.264格式的视频文件,读取每一帧,并将其转换为YUV格式:

extern "C" {#include <libavcodec/avcodec.h>#include <libavformat/avformat.h>
}int main() {// 注册所有的编解码器和格式av_register_all();// 打开视频文件AVFormatContext* formatContext = NULL;if (avformat_open_input(&formatContext, "a.h264", NULL, NULL) < 0) {// 错误处理...}// 查找视频流if (avformat_find_stream_info(formatContext, NULL) < 0) {// 错误处理...}int videoStreamIndex = -1;for (int i = 0; i < formatContext->nb_streams; i++) {if (formatContext->streams[i]->codecpar->codec_type == AVMEDIA_TYPE_VIDEO) {videoStreamIndex = i;break;}}if (videoStreamIndex == -1) {// 错误处理...}// 找到并打开解码器AVCodec* codec = avcodec_find_decoder(formatContext->streams[videoStreamIndex]->codecpar->codec_id);AVCodecContext* codecContext = avcodec_alloc_context3(codec);avcodec_parameters_to_context(codecContext, formatContext->streams[videoStreamIndex]->codecpar);if (avcodec_open2(codecContext, codec, NULL) < 0) {// 错误处理...}// 读取和解码视频帧AVPacket packet;AVFrame* frame = av_frame_alloc();while (av_read_frame(formatContext, &packet) >= 0) {if (packet.stream_index == videoStreamIndex) {if (avcodec_send_packet(codecContext, &packet) < 0) {// 错误处理...}while (avcodec_receive_frame(codecContext, frame) == 0) {// 此时,frame包含YUV数据// ... 处理frame的数据 ...}}av_packet_unref(&packet);}// 释放资源av_frame_free(&frame);avcodec_close(codecContext);avcodec_free_context(&codecContext);avformat_close_input(&formatContext);return 0;
}

在这个示例中,我们首先打开一个视频文件,并查找视频流。然后,我们找到并打开适当的解码器。接着,我们读取和解码视频帧,每当我们收到一个新的帧时,我们就处理它的YUV数据。最后,我们释放所有的资源。

利用SDL 把视频显示出来

在SDL2中,可以直接把YUV格式的数据显示出来,而且也比较容易,代码如下:

AVPacket packet;AVFrame* frame = av_frame_alloc();while (av_read_frame(pFormatCtx, &packet) >= 0) {if (packet.stream_index == videoindex) {if (avcodec_send_packet(codecContext, &packet) < 0) {// 错误处理...}while (avcodec_receive_frame(codecContext, frame) == 0) {// 此时,frame包含YUV数据//开始显示SDL_UpdateYUVTexture(sdlTexture, &sdlRect,frame->data[0], frame->linesize[0],frame->data[1], frame->linesize[1],frame->data[2], frame->linesize[2]);SDL_RenderClear(sdlRenderer);SDL_RenderCopy(sdlRenderer, sdlTexture, NULL, &sdlRect);SDL_RenderPresent(sdlRenderer);//SDL End-----------------------//Delay 1000/60ms--假设每分钟60帧SDL_Delay(1000/60);}av_packet_unref(&packet);}}

显示的效果如下:
在这里插入图片描述
刚才我们说过,YUV其实可以不用UV通道,可以让他显示为黑白的视频。修改一下代码,把UV通道都赋值为128,就可以看到灰色的效果了。

代码修改如下:

				memset(frame->data[1], 128, frame->linesize[1] * frame->height / 2);memset(frame->data[2], 128, frame->linesize[2] * frame->height / 2);SDL_UpdateYUVTexture(sdlTexture, &sdlRect,frame->data[0], frame->linesize[0],frame->data[1], frame->linesize[1],frame->data[2], frame->linesize[2]);

在这里插入图片描述
所有的代码都已在git上。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/121543.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

项目经验分享|openGauss 陈贤文:受益于开源,回馈于开源

开源之夏 项目经验分享 2023 #08 # 关于 openGauss 社区 openGauss是一款开源关系型数据库管理系统&#xff0c;采用木兰宽松许可证v2发行。openGauss内核深度融合华为在数据库领域多年的经验&#xff0c;结合企业级场景需求&#xff0c;持续构建竞争力特性。同时openGauss也是…

前后端交互系统:在Node.js中运行JavaScript

在Node.js中运行JavaScript&#xff0c;您需要编写适用于服务器端的代码&#xff0c;而不是浏览器端的代码。以下是一些示例代码&#xff0c;用于在Node.js中创建一个简单的HTTP服务器并在浏览器中访问它&#xff1a; // 引入Node.js内置的http模块 const http require(http);…

基于springboot实现校园志愿者管理系统项目【项目源码+论文说明】计算机毕业设计

基于springboot实现校园志愿者管理系统演示 摘要 随着信息化时代的到来&#xff0c;管理系统都趋向于智能化、系统化&#xff0c;校园志愿者管理系统也不例外&#xff0c;但目前国内仍都使用人工管理&#xff0c;市场规模越来越大&#xff0c;同时信息量也越来越庞大&#xff…

DevChat:VSCode中的AI黑马

前言 编程对于很多人来说&#xff0c;可能是一件复杂且耗时的事情。在结合当下各类AI产品层出不穷的情况下&#xff0c;我是有在认真的去拥抱AI来结合我们的工作&#xff0c;帮助我们的工作提升效率&#xff0c;尝试过我们的官方G P T&#xff0c;以及各类国产AI产品&#xff…

centos7虚拟机部署苍穹私有云环境记录

物理机建议16G内存以上&#xff0c;不然安装gpass过程中带不动虚拟机 步骤1&#xff1a;迅雷下载centos7.9镜像文件&#xff0c;并创建虚拟机&#xff0c;手动安装 http://ftp.sjtu.edu.cn/centos/7.9.2009/isos/x86_64/CentOS-7-x86_64-DVD-2009.iso 后面安装gpass时会有校验…

5.OsgEarth加载地形

愿你出走半生,归来仍是少年&#xff01; 在三维场景中除了使用影像体现出地貌情况&#xff0c;还需要通过地形体现出地势起伏&#xff0c;还原一个相对真实的三维虚拟世界。 osgEarth可通过直接加载Dem数据进行场景内的地形构建。 1.数据准备 由于我也没有高程数据&#xff0c…

【C程序设计】用心浇灌<C程序>

目录 数据类型 整数类型 实例 浮点类型 void 类型 类型转换 数据类型 在 C 语言中&#xff0c;数据类型指的是用于声明不同类型的变量或函数的一个广泛的系统。变量的类型决定了变量存储占用的空间&#xff0c;以及如何解释存储的位模式。 C 中的类型可分为以下几种&…

C++ 重载

C 允许在同一作用域中的某个函数和运算符指定多个定义&#xff0c;分别称为函数重载和运算符重载。 重载声明 是指一个与之前已经在该作用域内声明过的函数或方法具有相同名称的声明&#xff0c;但是它们的参数列表和定义&#xff08;实现&#xff09;不相同。 重载声明 当…

NSSCTF做题第9页(3)

[GKCTF 2020]CheckIN 代码审计 这段代码定义了一个名为ClassName的类&#xff0c;并在脚本的最后创建了一个ClassName类的实例。 在ClassName类的构造函数中&#xff0c;首先通过调用$this->x()方法获取了请求参数$_REQUEST中的值&#xff0c;并将其赋值给$this->code属性…

京东平台数据分析:2023年9月京东扫地机器人行业品牌销售排行榜

鲸参谋监测的京东平台9月份扫地机器人市场销售数据已出炉&#xff01; 根据鲸参谋平台的数据显示&#xff0c;9月份&#xff0c;京东平台扫地机器人的销量近14万&#xff0c;环比增长约2%&#xff0c;同比降低约4%&#xff1b;销售额为2.9亿&#xff0c;环比降低约4%&#xff0…

threejs(7)-精通粒子特效

一、初识Points与点材质 // 设置点材质 const pointsMaterial new THREE.PointsMaterial(); import * as THREE from "three"; // 导入轨道控制器 import { OrbitControls } from "three/examples/jsm/controls/OrbitControls"; // 导入动画库 import gsa…

Linux云服务器限制ip进行ssh远程连接

对Linux云服务器限制IP进行SSH远程连接的原因主要有以下几点&#xff1a; 增加安全性&#xff1a;SSH是一种加密的网络传输协议&#xff0c;可以保护数据的机密性和完整性。通过限制SSH连接的IP地址&#xff0c;可以防止未经授权的访问和数据泄露。只有拥有访问权限的IP地址才…

Makefile三个版本的编写

1.Makefile Makefile是一个工程管理文件&#xff0c;简化编译的流程&#xff0c;完成自动化编译的过程 在Makefile中&#xff0c;会把编译的过程分为两步&#xff0c;先生成.o文件&#xff0c;再对.o文件链接&#xff0c;生成可执行文件 Makefile由变量、函数、和规则构成 2.引…

辅助驾驶功能开发-执行器篇(03)-Mobileye Control Requirements

1. 目的 本文描述了产品开发不同阶段(研发、验证和产品化)车辆集成的控制要求。 2. 控制接口要求 2.1 接口类型 控制模块与车辆之间的接口应基于CAN协议或Flexray协议。 2.2 通讯频率 控制模块与车辆之间的通讯频率应高于36Hz。通信频率优先选择为 50 Hz。 2.3 延迟 所有…

vulnhub_DeRPnStiNK靶机渗透测试

VulnHub2018_DeRPnStiNK靶机 https://www.vulnhub.com/entry/derpnstink-1,221/ flag1(52E37291AEDF6A46D7D0BB8A6312F4F9F1AA4975C248C3F0E008CBA09D6E9166) flag2(a7d355b26bda6bf1196ccffead0b2cf2b81f0a9de5b4876b44407f1dc07e51e6) flag4(49dca65f362fee401292ed7ada96f9…

ResNet简单解释

什么是Resnet&#xff1f; resnet是一种残差网络&#xff0c;简单看一下resnet的结构 上面是ResNet&#xff0c;下面是传统的 ResNet里的一小块就是这样的 为什么要引入ResNet&#xff1f; 理论上讲&#xff0c;随着网络加深&#xff0c;我们获取的信息越来越多多&#xff0…

WordPress主题模板 大前端D8 5.1版本完整开源版源码简洁大气多功能配置

源码测评&#xff1a;该模板官方已更新至5.2&#xff0c;但是这个5.1也是非常好用的&#xff0c;经测试所有页面均完好&#xff0c;推荐下载使用。 模板简介&#xff1a; 大前端D8 主题是一款非常牛逼的WordPress博客主题,响应式,功能齐全,支持手机,电脑,平板,非常适合做博客站…

​iOS安全加固方法及实现

目录 iOS安全加固方法及实现 摘要 引言 iOS安全加固方法及实现 一、字符串加密 二、类名方法名混淆 三、程序代码混淆 四、加入安全SDK 总结 参考资料 摘要 本文介绍了iOS平台下的应用安全保护方法&#xff0c;包括字符串加密、类名方法名混淆、程序代码混淆和加入安全…

User CSS 在性能优化方面的实践

目录 前言 1. 减少重绘和回流 1.1 用法 1.2 代码示例 1.3 理解 2. 使用CSS精灵 2.1 用法 2.2 代码示例 2.3 理解 3. 压缩CSS文件 3.1 用法 3.2 代码示例 3.3 理解 4. 使用媒体查询进行响应式设计 4.1 用法 4.2 代码示例 4.3 理解 5. 使用CSS预处理器和构建工…

2015年亚太杯APMCM数学建模大赛A题海上丝绸之路发展战略的影响求解全过程文档及程序

2015年亚太杯APMCM数学建模大赛 A题 海上丝绸之路发展战略的影响 原题再现 一带一路不是实体或机制&#xff0c;而是合作与发展的理念和主张。凭借现有有效的区域合作平台&#xff0c;依托中国与有关国家现有的双边和多边机制&#xff0c;利用古丝绸之路的历史象征&#xff0…