当前位置: 首页 > news >正文

ffmpeg的重采样计算

最近在看ffmpeg的重采样计算逻辑,有一句话没大看懂 dst_nb_samples = av_rescale_rnd(swr_get_delay(swr_ctx, src_rate) + src_nb_samples, dst_rate, src_rate, AV_ROUND_UP); ,各种请教之后,记录如下。

重采样后的总样本数 为什么要涵盖重采样过程中的延迟 ?

在音频重采样过程中,由于源音频和目标音频的采样率不同,需要对音频数据进行插值或者抽取操作,以使其在时间上对齐。这个过程会引入一定的延迟。

延迟的引入是由于插值或抽取操作的特性决定的。例如,当将音频从低采样率转换为高采样率时,需要通过插值来生成新的样本,这会导致插值过程中的延迟。同样地,将音频从高采样率转换为低采样率时,需要通过抽取来减少样本数,这也会引入抽取过程中的延迟

为了确保重采样后的音频数据能够包含完整的有效音频信息,包括延迟期间的音频数据,我们需要计算重采样后的总样本数。这样可以确保在重采样过程中不会丢失任何音频信息。

因此,在计算重采样后的总样本数时,需要将源音频的样本数与重采样过程中产生的延迟相加。这样可以确保目标音频数据的长度足够容纳重采样过程中产生的延迟期间的音频数据,从而保证音频质量和完整性。

重采样后的总样本数如何计算?

重采样后的总样本数可以通过以下步骤计算:

  • 使用音频重采样上下文(swr_ctx)中的函数 swr_get_delay() 获取重采样引入的延迟(以源音频样本数为单位)。这个函数通常会返回一个浮点数,表示延迟的小数部分。

  • 将获取的延迟与源音频的样本数(src_nb_samples)相加,得到重采样后的未舍入的总样本数。这个值表示重采样后的音频数据中包含的总样本数,包括延迟期间的样本数。

  • 使用 FFmpeg 提供的函数 av_rescale_rnd() 将未舍入的总样本数按比例重新缩放,以适应目标音频的采样频率。

代码解释

这行代码是使用FFmpeg库中的函数进行音频重采样的过程中的一部分。

swr_ctx:这是一个音频重采样上下文(Context),它存储了音频重采样的状态信息和参数。

src_rate:这是源音频的采样率(采样频率),表示每秒钟采样的次数。

src_nb_samples:这是源音频中的样本数,表示要进行重采样的音频数据中包含的样本数。

swr_get_delay(swr_ctx, src_rate):swr_get_delay是一个函数,它返回进行音频重采样所需的延迟(以样本数为单位)。在这里,它返回源音频在重采样过程中产生的延迟。

swr_get_delay(swr_ctx, src_rate) + src_nb_samples:这个表达式将源音频的样本数和重采样过程中的延迟相加,得到重采样后的总样本数。

dst_rate:这是目标音频的采样率,表示重采样后的音频的采样率。

av_rescale_rnd():这是一个函数,用于将一个值按比例重新缩放。它接受要缩放的值、缩放的目标范围和要使用的舍入模式(rounding mode)作为参数,并返回缩放后的结果。

av_rescale_rnd(swr_get_delay(swr_ctx, src_rate) + src_nb_samples, dst_rate, src_rate, AV_ROUND_UP):这个表达式将重采样后的总样本数按比例重新缩放,使其适应目标音频的采样率。AV_ROUND_UP是一个舍入模式,表示采用向上舍入的方式。

dst_nb_samples:这是重采样后的目标音频的样本数。

总而言之,这行代码的目的是计算重采样后的目标音频的样本数。它通过将源音频的样本数和重采样过程中产生的延迟相加,并按比例重新缩放以适应目标音频的采样率来实现。

音频连续时间戳计算逻辑分析

看下这段代码

   ret = avcodec_receive_frame(d->avctx, frame);if (ret >= 0) {AVRational tb = (AVRational){1, frame->sample_rate};if (frame->pts != AV_NOPTS_VALUE)frame->pts = av_rescale_q(frame->pts, d->avctx->pkt_timebase, tb);else if (d->next_pts != AV_NOPTS_VALUE)frame->pts = av_rescale_q(d->next_pts, d->next_pts_tb, tb);if (frame->pts != AV_NOPTS_VALUE) {d->next_pts = frame->pts + frame->nb_samples;d->next_pts_tb = tb;}}

frame->pts = av_rescale_q(frame->pts, d->avctx->pkt_timebase, tb)的含义

时间跨度= 当前应出现时间-初始时间 = 源时间戳 * 源时间基数 = 目标时间戳 * 目标时间基数

这行代码是用于将帧的时间戳(PTS)从一个时间基(timebase)转换为另一个时间基的操作。即 目标时间戳 = 源时间戳 * 源时间基数 / 目标时间基数

在这行代码中,frame->pts表示当前帧的时间戳。d->avctx->pkt_timebase表示编码器上下文(AVCodecContext)中的数据包时间基。tb则表示目标时间基。

av_rescale_q函数用于执行时间戳的转换。它接受三个参数:源值(即当前帧的时间戳),源时间基和目标时间基。函数会根据提供的时间基参数,将源值从源时间基转换为目标时间基,并返回转换后的值作为结果。

通过这个操作,可以将帧的时间戳从一个时间基转换为另一个时间基,以适应不同的容器或编解码器要求。这对于正确处理时间轴和时序是非常重要的,特别是在处理音视频同步、编辑和混流等操作时。这种转换可以确保视频和音频的时间信息在不同的上下文中保持一致和准确。

d->next_pts = frame->pts + frame->nb_samples;

假设每个音频样本的持续时间都是1/sample_count_per_second,那么存在等式:当前时间戳(单位秒)+当前音频帧的样本个数 = 下一个音频帧的开始时间戳(单位秒),据此,我们解释一下这行代码。

在这行代码中,frame->pts表示源值,即当前帧的时间戳(Presentation Timestamp,PTS)。d->avctx->pkt_timebase表示源时间基,它是编码器上下文(AVCodecContext)中的数据包时间基。

时间基是一个分数,用于表示时间的单位和精度。它通常用于将时间戳从一种表示方式转换为另一种表示方式。分数的分子表示时间单位,分母表示每秒的时间单位数。

在这里,frame->pts乘以d->avctx->pkt_timebase的目的是将当前帧的时间戳从源时间基转换为目标时间基。乘法运算的结果是一个根据源时间基和目标时间基的比例进行缩放的时间戳值。

通过执行乘法运算,可以将时间戳从一个时间基转换为另一个时间基,以便在不同的容器或编解码器之间进行正确的时间同步和时间轴处理。这种转换可以确保视频和音频的时间信息在不同的上下文中保持一致和准确。

frame->pts = av_rescale_q(d->next_pts, d->next_pts_tb, tb);

根据上面的推算,其实d->next_pts的时间基已经不是解码的时间基了,而是解码后的时间基,即目标采样率1/sample_count_per_second,所以这里有 d->next_pts_tb = tb;

音频序列号分析

d->pkt_serial是一个变量,用于表示音视频数据包的序列号。在音视频处理和同步过程中,使用序列号可以跟踪和标识不同的音视频数据包。

序列号通常用于多线程或并行处理的场景,其中音频和视频数据可能以不同的速度解码和处理。每个数据包都可以被分配一个唯一的序列号,以便在后续的处理过程中进行识别和排序。

通过使用序列号,可以实现以下功能:

  1. 数据包排序:通过比较不同数据包的序列号,可以按正确的顺序对它们进行处理,以确保音视频数据的正确同步。例如,在音视频同步中,可以根据序列号将音频和视频数据包按照时间顺序进行匹配和呈现。

  2. 错误检测:序列号可以用于检测丢失的或乱序的数据包。如果一个或多个数据包的序列号在处理过程中出现间隔或不连续,可能表明存在数据包丢失或乱序的问题。

  3. 数据包关联:序列号还可以用于将音频和视频数据包进行关联。例如,在多个音频和视频流进行混流的情况下,可以通过序列号将对应的音频和视频数据包进行匹配和关联。

综上所述,d->pkt_serial是一个用于标识和跟踪音视频数据包的序列号变量,用于实现数据包的排序、错误检测和关联等功能。

音频包处理

pkt_in_play_range 是一个表示音视频包(packet)是否处于播放范围内的标志。它通常用于音视频播放器或处理器中,以确定是否应该处理给定的音视频包。

在音视频处理中,往往会有一个播放范围(play range),用于指定在特定时间段内播放音视频数据。播放范围可以是整个音视频文件的时间范围,也可以是用户在播放器中指定的某个时间段。

pkt_in_play_range 标志用于判断当前的音视频包是否在播放范围内。如果 pkt_in_play_range 为真(非零),表示音视频包处于播放范围内,应该被处理和播放。如果 pkt_in_play_range 为假(零),表示音视频包不在播放范围内,可以选择跳过处理或忽略该包。

这个标志的设置通常由播放器或相关的音视频处理逻辑根据当前的播放位置和播放范围来决定。它可以帮助控制音视频的播放和处理,以确保只处理和呈现播放范围内的音视频数据。

相关文章:

ffmpeg的重采样计算

最近在看ffmpeg的重采样计算逻辑,有一句话没大看懂 dst_nb_samples av_rescale_rnd(swr_get_delay(swr_ctx, src_rate) src_nb_samples, dst_rate, src_rate, AV_ROUND_UP); ,各种请教之后,记录如下。 重采样后的总样本数 为什么要涵盖重采…...

Go HTTP 调用(上)

哈喽大家好,我是陈明勇,今天分享的内容是 Go HTTP 调用。如果本文对你有帮助,不妨点个赞,如果你是 Go 语言初学者,不妨点个关注,一起成长一起进步,如果本文有错误的地方,欢迎指出&am…...

STM32Cube高效开发教程<基础篇>(一)----概述

声明:本人水平有限,博客可能存在部分错误的地方,请广大读者谅解并向本人反馈错误。    本专栏博客参考《STM32Cube高效开发教程(基础篇)》,有意向的读者可以购买正版书籍辅助学习,本书籍由王维波老师、鄢志丹老师、王钊老师倾力打造,书籍内容干货满满。 一、 STM32系列…...

汽车RNC主动降噪算法DSP C程序实现

汽车RNC主动降噪算法C程序 是否需要申请加入数字音频系统研究开发交流答疑群(课题组)?可加我微信hezkz17, 本群提供音频技术答疑服务,车载...

Java21虚拟线程完整用法

方式1 Thread.startVirtualThread(new Task());方式2 Thread virtualThread Thread.ofVirtual().name("Virtual Thread").unstarted(new Task()); virtualThread.start();方式3 Thread.ofVirtual().name("Virtual Thread").start(new Task());方式4 Th…...

Vue 中的 nextTick 方法

nextTick的背景 Vue 使用虚拟 DOM(Virtual DOM)和异步更新策略来实现高效的视图更新。当你修改 Vue 实例的数据时,Vue 并不会立即更新真实的 DOM,而是将更新操作加入到队列中,在下一个事件循环周期(微任务…...

TypeScript React(上)

目录 扩展学习资料 TypeScript设计原则 TypeScript基础 语法基础 变量声明 JavaScript声明变量 TypeScript声明变量 示例 接口 (标准类型-Interface) 类型别名-Type 接口 VS 类型别名 类型断言:欺骗TS&#xff0c;肯定数据符合结构 泛型、<大写字母> 扩展学习…...

Linux 安全 - LSM源码分析

文章目录 前言一、简介1.1 DAC 和 MAC1.2 LSM 调用流程图 二、LSM相关数据结构2.1 struct security_hook_list2.2 union security_list_options2.3 structure security_hook_heads 三、security_bprm_check四、LSM 源码分析3.1 early_security_init3.2 security_init3.2.1 secu…...

第一次汇报相关问题

深度学习现在已经学习到了Mini-Batch&#xff0c;early-stop等针对特定场景优化的算法了。 代码已经实现了一个L层的神经网络的构建了 论文看了一些综述 主要思考的两个方向&#xff1a;云计算和嵌入式 云计算&#xff1a;分布式机器学习、联邦学习、服务器负载均衡等 嵌入式&…...

[产品体验] GPT4识图功能

[产品体验] GPT4识图功能 图片配文字超强的OCR能力知识问答多图解释 打开chatgpt的时候突然发现能用识图了&#xff0c;赶紧去体验一下&#xff0c;大大的震撼… 图片配文字 超强的OCR能力 我传上去的图片并不清晰… 还能准确识别&#xff0c;orz &#xff01; 知识问答 多…...

《3D 数学基础》几何检测-最近点

目录 1. 直线上的最近点 2. 射线上的最近点 3. 点到平面的距离 4. 圆或球上的最近点 5. AABB上的最近点 1. 直线上的最近点 q是距离q的最近点&#xff0c;也就是q在直线上的投影。 其中p是直线上的点&#xff08;向量表示&#xff09;&#xff0c;n是直线的法向量&#x…...

动态规划 -背包问题-详解

问题 注&#xff1a;大佬对此类问题的解法&#xff1a;动态规划背包问题总结 给你一个由 不同 整数组成的数组 nums &#xff0c;和一个目标整数 target 。请你从 nums 中找出并返回总和为 target 的元素组合的个数。 题目数据保证答案符合 32 位整数范围。 示例 1&#xff…...

Bootstrap-- 媒体特性

最大、最小宽度例子&#xff1a; 横屏与竖屏例子&#xff1a; 宽度比与像素比例子&#xff1a;...

c# 用非递归的写法实现递归

最近写代码碰到了一个bug&#xff0c;就是递归次数太多爆堆栈了&#xff0c;然后就写了一个递归工具来解决这个问题。 using System; using System.Collections.Generic;/// <summary> /// 递归工具 /// </summary> public static class RecursionTool {//递归方式…...

nginx之location的优先级和nginx的重定向

一、nginx之location的优先级和匹配方式&#xff08;重点&#xff09; &#xff08;一&#xff09;nginx的正则表达式 nginx的正则表达式 符号 含义 ^ 字符串的起始位置&#xff08;以什么开头&#xff09; $ 字符串的结束位置&#xff08;以什么结尾&#xff09; * 匹…...

【计算机网络】——前言计算机网络发展的历程概述

主页点击直达&#xff1a;个人主页 我的小仓库&#xff1a;代码仓库 C语言偷着笑&#xff1a;C语言专栏 数据结构挨打小记&#xff1a;初阶数据结构专栏 Linux被操作记&#xff1a;Linux专栏 LeetCode刷题掉发记&#xff1a;LeetCode刷题 算法&#xff1a;算法专栏 C头…...

eventfd

1. #include <sys/eventfd.h> int eventfd(unsigned int initval, int flags); //创建eventfd 参数含义&#xff1a; initval&#xff1a;创建eventfd时它所对应的64位计数器的初始值&#xff1b; flags&#xff1a;eventfd文件描述符的标志&#xff0c;可由三种选项组…...

BES耳机空间音频技术实现

BES耳机空间音频技术实现 是否需要申请加入数字音频系统研究开发交流答疑群(课题组)?加我微信hezkz17, 本群提供音频技术答疑服务 音响和耳机在空间音频技术上实现方式是不同的 虚拟现实可谓是空间音频技术最具代表性的应 用领域。虽然虚拟现实的起源可以追溯到1 9 6 8年, …...

day27--AJAX(bootstrap之modal,toast;接口文档的一些用法;AJAX原理)

目录 Bootstrap之Modal&#xff1a; 显示和隐藏方法 通过自定义属性&#xff1a; 使用JS来控制弹框&#xff1a; Bootstrap之Toast&#xff1a; 接口文档一些用法&#xff1a; 删除图书&#xff1a; 图片上传&#xff1a; 图片上传步骤&#xff1a; 修改头像&#xf…...

【ArcGIS Pro二次开发】(70):杂七杂八的记录

本文用于记录一些使用频率较高但归类繁杂&#xff0c;非系统性的一些代码。 主要方便自己使用和查阅&#xff0c;随时更新。 1、从GDB数据库中打开【FeatureDataset\FeatureClass\Table】 using Geodatabase gdb new Geodatabase(new FileGeodatabaseConnectionPath(new Uri…...

测试微信模版消息推送

进入“开发接口管理”--“公众平台测试账号”&#xff0c;无需申请公众账号、可在测试账号中体验并测试微信公众平台所有高级接口。 获取access_token: 自定义模版消息&#xff1a; 关注测试号&#xff1a;扫二维码关注测试号。 发送模版消息&#xff1a; import requests da…...

云启出海,智联未来|阿里云网络「企业出海」系列客户沙龙上海站圆满落地

借阿里云中企出海大会的东风&#xff0c;以**「云启出海&#xff0c;智联未来&#xff5c;打造安全可靠的出海云网络引擎」为主题的阿里云企业出海客户沙龙云网络&安全专场于5.28日下午在上海顺利举办&#xff0c;现场吸引了来自携程、小红书、米哈游、哔哩哔哩、波克城市、…...

FFmpeg 低延迟同屏方案

引言 在实时互动需求激增的当下&#xff0c;无论是在线教育中的师生同屏演示、远程办公的屏幕共享协作&#xff0c;还是游戏直播的画面实时传输&#xff0c;低延迟同屏已成为保障用户体验的核心指标。FFmpeg 作为一款功能强大的多媒体框架&#xff0c;凭借其灵活的编解码、数据…...

Java - Mysql数据类型对应

Mysql数据类型java数据类型备注整型INT/INTEGERint / java.lang.Integer–BIGINTlong/java.lang.Long–––浮点型FLOATfloat/java.lang.FloatDOUBLEdouble/java.lang.Double–DECIMAL/NUMERICjava.math.BigDecimal字符串型CHARjava.lang.String固定长度字符串VARCHARjava.lang…...

sqlserver 根据指定字符 解析拼接字符串

DECLARE LotNo NVARCHAR(50)A,B,C DECLARE xml XML ( SELECT <x> REPLACE(LotNo, ,, </x><x>) </x> ) DECLARE ErrorCode NVARCHAR(50) -- 提取 XML 中的值 SELECT value x.value(., VARCHAR(MAX))…...

AspectJ 在 Android 中的完整使用指南

一、环境配置&#xff08;Gradle 7.0 适配&#xff09; 1. 项目级 build.gradle // 注意&#xff1a;沪江插件已停更&#xff0c;推荐官方兼容方案 buildscript {dependencies {classpath org.aspectj:aspectjtools:1.9.9.1 // AspectJ 工具} } 2. 模块级 build.gradle plu…...

Maven 概述、安装、配置、仓库、私服详解

目录 1、Maven 概述 1.1 Maven 的定义 1.2 Maven 解决的问题 1.3 Maven 的核心特性与优势 2、Maven 安装 2.1 下载 Maven 2.2 安装配置 Maven 2.3 测试安装 2.4 修改 Maven 本地仓库的默认路径 3、Maven 配置 3.1 配置本地仓库 3.2 配置 JDK 3.3 IDEA 配置本地 Ma…...

以光量子为例,详解量子获取方式

光量子技术获取量子比特可在室温下进行。该方式有望通过与名为硅光子学&#xff08;silicon photonics&#xff09;的光波导&#xff08;optical waveguide&#xff09;芯片制造技术和光纤等光通信技术相结合来实现量子计算机。量子力学中&#xff0c;光既是波又是粒子。光子本…...

CSS设置元素的宽度根据其内容自动调整

width: fit-content 是 CSS 中的一个属性值&#xff0c;用于设置元素的宽度根据其内容自动调整&#xff0c;确保宽度刚好容纳内容而不会超出。 效果对比 默认情况&#xff08;width: auto&#xff09;&#xff1a; 块级元素&#xff08;如 <div>&#xff09;会占满父容器…...

浪潮交换机配置track检测实现高速公路收费网络主备切换NQA

浪潮交换机track配置 项目背景高速网络拓扑网络情况分析通信线路收费网络路由 收费汇聚交换机相应配置收费汇聚track配置 项目背景 在实施省内一条高速公路时遇到的需求&#xff0c;本次涉及的主要是收费汇聚交换机的配置&#xff0c;浪潮网络设备在高速项目很少&#xff0c;通…...