ffplay源码分析-main函数入口分析
ffplay源码分析-main函数入口分析
基于ffmpeg6.0源码分析。
流程
使用ffplay播放视频文件,会触发main函数的调用。main函数中会进行以下操作:
- 从命令行中解析日志级别、日志是否需要落文件、是否要输出banner信息。banner信息包含版权、库的版本。
- 注册解码器、复用器、协议。
- avdevice_register_all会将输出formats和输入formats注册到allformats.c的变量中。
allformat.c
void avpriv_register_devices(const FFOutputFormat * const o[], const AVInputFormat * const i[])
{// 还是个原子操作赋值。atomic_store_explicit(&outdev_list_intptr, (uintptr_t)o, memory_order_relaxed);atomic_store_explicit(&indev_list_intptr, (uintptr_t)i, memory_order_relaxed);
}
alldevices.c
void avdevice_register_all(void)
{avpriv_register_devices(outdev_list, indev_list);
}
其中outdev_list来自outdev_list.c文件,idev_list来自indev_list.c文件。这2个文件是自动生成的。所以我猜它是根据我们不同的配置来生成不同的内容。
我的indev_list.c
static const AVInputFormat * const indev_list[] = {
&ff_avfoundation_demuxer,
&ff_lavfi_demuxer,
NULL };
我的outdev_list.c
static const FFOutputFormat * const outdev_list[] = {
&ff_audiotoolbox_muxer,
&ff_sdl2_muxer,
NULL };
- 初始化网络,会根据使用的是openssl还是guntls进行初始化,对于window,有可能需要调用一下WSAStartup,ms-socket。
void ff_tls_deinit(void)
{
#if CONFIG_TLS_PROTOCOL
#if CONFIG_OPENSSLff_openssl_deinit();
#endif
#if CONFIG_GNUTLSff_gnutls_deinit();
#endif
#endif
}int ff_network_init(void)
{
#if HAVE_WINSOCK2_HWSADATA wsaData;// Windowsif (WSAStartup(MAKEWORD(1,1), &wsaData))return 0;
#endifreturn 1;
}
- 监听程序退出信号,这一步是为了能响应用户关闭程序的操作。比如在播放过程中,在命令行中按ctrl-c就会退出程序。
static void sigterm_handler(int sig)
{exit(123);
}
- 显示banner信息,banner信息包含版本、配置等。
void show_banner(int argc, char **argv, const OptionDef *options)
{int idx = locate_option(argc, argv, options, "version");if (hide_banner || idx)return;// 打印ffmpeg的版本,版权信息、配置信息print_program_info (INDENT|SHOW_COPYRIGHT, AV_LOG_INFO);// 打印子库的配置信息print_all_libs_info(INDENT|SHOW_CONFIG, AV_LOG_INFO);// 打印字库的版本信息print_all_libs_info(INDENT|SHOW_VERSION, AV_LOG_INFO);
}
- 解析命令行参数,得到需要播放的文件,解析成功之后全局变量input_filename存储的就是输入的文件。
void parse_options(void *optctx, int argc, char **argv, const OptionDef *options,void (*parse_arg_function)(void *, const char*))
{const char *opt;int optindex, handleoptions = 1, ret;prepare_app_arguments(&argc, &argv); // 空的,不用管optindex = 1;while (optindex < argc) {opt = argv[optindex++];if (handleoptions && opt[0] == '-' && opt[1] != '\0') {if (opt[1] == '-' && opt[2] == '\0') {handleoptions = 0; // 如果参数是"--" ,即没有拼参数名,则跳过。continue;}opt++;// 如果小于0,说明解析参数发生了错误。if ((ret = parse_option(optctx, opt, argv[optindex], options)) < 0)exit_program(1); // 退出程序。optindex += ret;} else {if (parse_arg_function) // 如果上一个参数是跳过的(handleoptiongs是0),或者参数不是"-"开始的一个字符串,不能只是一个"-",则执行这个函数。parse_arg_function(optctx, opt); // 这种情况opt可能是要处理文件。}}
}
// parse_arg_function 就指向这个函数:
static void opt_input_file(void *optctx, const char *filename)
{if (input_filename) {av_log(NULL, AV_LOG_FATAL,"Argument '%s' provided as input filename, but '%s' was already specified.\n",filename, input_filename);exit(1);}if (!strcmp(filename, "-"))filename = "fd:";input_filename = filename; // 要播放的输入文件。
}
- 如果没解析到要播放的文件,输出帮助信息,并退出程序。
- 初始化SDL库,ffplay播放音频、视频都用到SDL库。
- 根据用户的配置、SDL的版本、来设置SDL显示窗口的配置,比如是否显示窗口边界。使用默认大小来创建一个SDL窗口。
int flags = SDL_WINDOW_HIDDEN;if (alwaysontop)
#if SDL_VERSION_ATLEAST(2,0,5)flags |= SDL_WINDOW_ALWAYS_ON_TOP;
#elseav_log(NULL, AV_LOG_WARNING, "Your SDL version doesn't support SDL_WINDOW_ALWAYS_ON_TOP. Feature will be inactive.\n");
#endifif (borderless) // 命令参数可以控制flags |= SDL_WINDOW_BORDERLESS; // 控制SDL显示的窗口是否需要边界elseflags |= SDL_WINDOW_RESIZABLE;#ifdef SDL_HINT_VIDEO_X11_NET_WM_BYPASS_COMPOSITORSDL_SetHint(SDL_HINT_VIDEO_X11_NET_WM_BYPASS_COMPOSITOR, "0");
#endif// 使用默认大小、窗口配置flags创建窗口。window = SDL_CreateWindow(program_name, SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, default_width, default_height, flags);SDL_SetHint(SDL_HINT_RENDER_SCALE_QUALITY, "linear"); // https://wiki.libsdl.org/SDL2/SDL_HINT_RENDER_SCALE_QUALITY
- 创建renderer,renderer是SDK绘制图形必须要用到的东西。以及是否有可用的texture。
if (window) {// 创建renderer, 可以用这个画图形。renderer = SDL_CreateRenderer(window, -1, SDL_RENDERER_ACCELERATED | SDL_RENDERER_PRESENTVSYNC);if (!renderer) {av_log(NULL, AV_LOG_WARNING, "Failed to initialize a hardware accelerated renderer: %s\n", SDL_GetError());renderer = SDL_CreateRenderer(window, -1, 0);}if (renderer) {if (!SDL_GetRendererInfo(renderer, &renderer_info)) // 获取renderer的信息。av_log(NULL, AV_LOG_VERBOSE, "Initialized %s renderer.\n", renderer_info.name);}}if (!window || !renderer || !renderer_info.num_texture_formats) { // 如果没有渲染的条件,则退出程序。av_log(NULL, AV_LOG_FATAL, "Failed to create window or renderer: %s", SDL_GetError());do_exit(NULL);}...
- 打开输入文件。
- 进入循环,监听键盘、鼠标事件,循环渲染视频。
代码
int main(int argc, char **argv)
{int flags;VideoState *is; // 用来保存全局状态init_dynload(); // 仅window会有用,安全问题,会将当前目录从DLL库搜索目录中删除。av_log_set_flags(AV_LOG_SKIP_REPEATED); // 设置日志如果是重复文案是否跳过parse_loglevel(argc, argv, options); // 从参数中解析日志级别、日志是否要落文件、是否要输出banner信息。/* register all codecs, demux and protocols */
#if CONFIG_AVDEVICEavdevice_register_all();
#endifavformat_network_init();// 处理用户退出程序操作。 https://zh.m.wikipedia.org/wiki/Unix%E4%BF%A1%E5%8F%B7#SIGTERMsignal(SIGINT , sigterm_handler); /* Interrupt (ANSI). Ctrl-C */signal(SIGTERM, sigterm_handler); /* Termination (ANSI). when user terminate */// 显示banner, 就是打印动态库的版权、版本等信息。show_banner(argc, argv, options);parse_options(NULL, argc, argv, options, opt_input_file);if (!input_filename) {show_usage(); // 如果没有从参数中解析出要播放的文件,输出错误日志提示用户,并退出程序。av_log(NULL, AV_LOG_FATAL, "An input file must be specified\n");av_log(NULL, AV_LOG_FATAL,"Use -h to get full help or, even better, run 'man %s'\n", program_name);exit(1);}if (display_disable) { // 用户参数可以控制这个开关,默认关闭。video_disable = 1;}flags = SDL_INIT_VIDEO | SDL_INIT_AUDIO | SDL_INIT_TIMER; // 设置SDL初始化时的flags。包含了SDL音频子系统、SDL视频子系统、SDL时间子系统、事件子系统。if (audio_disable) // // 用户参数可以控制这个开关,默认关闭。flags &= ~SDL_INIT_AUDIO;else {/* Try to work around an occasional ALSA buffer underflow issue when the* period size is NPOT due to ALSA resampling by forcing the buffer size. */if (!SDL_getenv("SDL_AUDIO_ALSA_SET_BUFFER_SIZE")) // 奇怪的fix.SDL_setenv("SDL_AUDIO_ALSA_SET_BUFFER_SIZE","1", 1);}if (display_disable)flags &= ~SDL_INIT_VIDEO;if (SDL_Init (flags)) { // 初始化SDL,https://wiki.libsdl.org/SDL2/SDL_Initav_log(NULL, AV_LOG_FATAL, "Could not initialize SDL - %s\n", SDL_GetError());av_log(NULL, AV_LOG_FATAL, "(Did you set the DISPLAY variable?)\n");exit(1);}// 不监听系统事件和用户自定义事件。https://wiki.libsdl.org/SDL2/SDL_EventSDL_EventState(SDL_SYSWMEVENT, SDL_IGNORE);SDL_EventState(SDL_USEREVENT, SDL_IGNORE);if (!display_disable) {int flags = SDL_WINDOW_HIDDEN;if (alwaysontop)
#if SDL_VERSION_ATLEAST(2,0,5)flags |= SDL_WINDOW_ALWAYS_ON_TOP;
#elseav_log(NULL, AV_LOG_WARNING, "Your SDL version doesn't support SDL_WINDOW_ALWAYS_ON_TOP. Feature will be inactive.\n");
#endifif (borderless)flags |= SDL_WINDOW_BORDERLESS; // 控制SDL显示的窗口是否需要边界elseflags |= SDL_WINDOW_RESIZABLE;#ifdef SDL_HINT_VIDEO_X11_NET_WM_BYPASS_COMPOSITORSDL_SetHint(SDL_HINT_VIDEO_X11_NET_WM_BYPASS_COMPOSITOR, "0");
#endif// 使用默认大小、窗口配置flags创建窗口。window = SDL_CreateWindow(program_name, SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, default_width, default_height, flags);SDL_SetHint(SDL_HINT_RENDER_SCALE_QUALITY, "linear"); // https://wiki.libsdl.org/SDL2/SDL_HINT_RENDER_SCALE_QUALITYif (window) {// 创建renderer, 可以用这个画图形。renderer = SDL_CreateRenderer(window, -1, SDL_RENDERER_ACCELERATED | SDL_RENDERER_PRESENTVSYNC);if (!renderer) {av_log(NULL, AV_LOG_WARNING, "Failed to initialize a hardware accelerated renderer: %s\n", SDL_GetError());renderer = SDL_CreateRenderer(window, -1, 0);}if (renderer) {if (!SDL_GetRendererInfo(renderer, &renderer_info)) // 获取renderer的信息。av_log(NULL, AV_LOG_VERBOSE, "Initialized %s renderer.\n", renderer_info.name);}}if (!window || !renderer || !renderer_info.num_texture_formats) { // 如果没有渲染的条件,则退出程序。av_log(NULL, AV_LOG_FATAL, "Failed to create window or renderer: %s", SDL_GetError());do_exit(NULL);}}// 打开输入文件, 如果用户强制设置了fmt file_iformat则不为nullis = stream_open(input_filename, file_iformat);if (!is) {av_log(NULL, AV_LOG_FATAL, "Failed to initialize VideoState!\n");do_exit(NULL);}// 循环,监听键盘事件、刷新界面。event_loop(is); /* never returns */return 0;
}
相关文章:
![](https://www.ngui.cc/images/no-images.jpg)
ffplay源码分析-main函数入口分析
ffplay源码分析-main函数入口分析 基于ffmpeg6.0源码分析。 流程 使用ffplay播放视频文件,会触发main函数的调用。main函数中会进行以下操作: 从命令行中解析日志级别、日志是否需要落文件、是否要输出banner信息。banner信息包含版权、库的版本。注…...
![](https://img-blog.csdnimg.cn/img_convert/5f2e6a76ab868532793d7586f1920a0f.png)
C++三种继承方式
C继承的一般语法为:class 派生类名:[继承方式] 基类名{派生类新增加的成员};继承方式限定了基类成员在派生类中的访问权限,包括 public(公有的)、private(私有的)和 protected&#…...
![](https://img-blog.csdnimg.cn/4f90db9be93a48b29f3b63e9a789cc7f.png)
【Android -- 软技能】《软技能:代码之外的生存指南》之好书推荐(一)
前言 这是一本由美国的一个软件开发人员写的,但书中除了有 Java 、C# 几个单词外,没有一行代码。 因为这本书讲的是代码之外的东西。 文章目录结构: 1. 职业 从业心态:说白了就是要有责任心,把每份工作要当成是自…...
![](https://www.ngui.cc/images/no-images.jpg)
Nginx可视化管理工具 - Nginx Proxy Manager
一、介绍 nginx-proxy-manager 是一个反向代理管理系统,它基于Nginx,具有漂亮干净的 Web UI。还可以获得受信任的 SSL 证书,并通过单独的配置、自定义和入侵保护来管理多个代理。 其官网地址如下: https://nginxproxymanager.com/ 二、安装 第一步:192.168.1.108服务…...
![](https://www.ngui.cc/images/no-images.jpg)
https是如何保证安全的
在学习http与https的区别的时候,我们通常从以下几点出发:http是超文本传输协议,是明文传输,有安全风险,https在TCP和http网络层之间加入了SSL/TLS安全协议,使得报文能够加密传输http连接简单,三…...
![](https://www.ngui.cc/images/no-images.jpg)
ubuntu下使用GCC开发单片机的过程
以下是一个简单的单片机C程序示例,实现的功能是控制LED灯的闪烁: #include <reg52.h> // 导入单片机的寄存器定义void main() {while(1) { // 无限循环P1 = 0x00; // P1口输出低电平delay(1000); // 延时1秒P1 = 0xff; // P1口输出高电平delay(1000); // 延时1秒…...
![](https://img-blog.csdnimg.cn/7b51f358abf14106bb9807cde48325fc.png)
人工智能能否取代软硬件开发工程师
版权声明 本文原创作者:谷哥的小弟作者博客地址:http://blog.csdn.net/lfdfhl 人工智能发展趋势 随着AI技术的不断发展,它正在改变我们的生活方式、商业模式和工作方式。人工智能技术的发展一直处于快速变化和持续创新的状态,以下…...
![](https://www.ngui.cc/images/no-images.jpg)
BPI-R3开发板 - uboot编译
一. 获取源码 https://github.com/mtk-openwrt/u-boot 二. 编译步骤 编译环境为ubuntu 18.04。交叉编译工具链我用的是openwrt编译生成的工具链,并设置到环境变量,如下: export PATH$PATH:/root/mt8976/BPI-R3-OPENWRT-V21.02.3-main/staging…...
![](https://img-blog.csdnimg.cn/img_convert/dee99cdfc5c2cfa3df82b90f978a4ef1.webp?x-oss-process=image/format,png)
优秀程序员的5个特征,你在第几层?
每个人程序员都对未来的职业发展有着憧憬和规划,要做架构师、要做技术总监、要做CTO。但现实总是复杂的,日复一日的工作与生活总能让人一次又一次地陷入迷茫。大部分原因就是对职业发展轨迹和自我能力提升的一般规律缺乏认识,做事找不到方向或…...
![](https://img-blog.csdnimg.cn/420c67c057174a8784d94c25e549704f.png)
JAVA Session会话 Thymeleaf - 视图模板技术配置步骤
JAVAWebSession会话会话跟踪技术session保存作用域Thymeleaf - 视图模板技术配置过程Session会话 HTTP是无状态的:服务器无法区分这两个请求是同一个客户端发过来的,还是不同的客户端发过来的 现实问题:第一次请求是添加商品到购物车&#x…...
![](https://www.ngui.cc/images/no-images.jpg)
Linux编译cpprestsdk库
本文用的Linux系统为Ubuntu22.04,自带GCC11.3.0。 依赖 ①编译需要boost库,本文用的库版本为boost-1.82.0.beta1.tar.gz。 ②编译需要openssl库,这里使用的版本为openssl-1.1.1s.tar.gz。 ③编译需要cmake库,本文使用的是cmake-3…...
![](https://img-blog.csdnimg.cn/c4e569fe36c349399afe29322bfc5c83.png)
算法的时间复杂度和空间复杂度
目录 1 如何衡量一个算法的好坏 2.时间复杂度 2.1 时间复杂度的概念 2.2 大O的渐进表示法 2.3常见代码举例 2.3.1 Func2 O(N) 2.3.2 Func3 O(MN) 2.3.3 Func4 O(1) 2.3.4 Func5 strchr O(N) 2.3.5 Func6 冒泡排序 O(N^2) 2.3.6 Func7 二分…...
![](https://img-blog.csdnimg.cn/7f5b4bc9ddc5498483f4f0263c16d119.png)
基本认识vue3
一、基本搭建 项目搭建 使用 最新的 Vue3 TS Vite项目 执行命令 (本项目采用如下方式) npm create vitelatest my-vite-app --template vue-ts或者 运行项目 npm install npm run dev项目搭建初始化目录 新搭建的项目可能会遇到个问题…...
![](https://img-blog.csdnimg.cn/img_convert/ec7613eb1a115448276e30dc0bff3bd1.png)
HTTP/HTTPS协议认识
写在前面 这个博客我们要要讨论的是协议,主要是应用层.今天我们将正式认识HTTP和HTTPS,也要认识序列化和反序列化,内容比较多,但是不难 再谈协议 我们程序员写的一个个解决我们实际问题, 满足我们日常需求的网络程序, 都是在应用层,我们要完成下面三个步骤. sock的使用 定制…...
![](https://img-blog.csdnimg.cn/1391aa8239204a4580db049f4475498f.png)
【VScode】远程连接Linux
目录标题1. 安装扩展插件2. 在Linux上操作3. 确定Linux的IP地址4. 远程连接到Linux5. 实现免密码登录使用 VScode 远程编程与调试的时有会用到插件 Remote Development,使用这个插件可以在很多情况下代替 vim 直接远程修改与调试服务器上的代码,同时具备…...
![](https://img-blog.csdnimg.cn/1974fe2662da40059d545acbb5975343.png)
QT/C++调试技巧:内存泄漏检测
文章目录内存泄漏方案一方案二:CRT调试定位代码位置方法1方法2其它问题方案三:使用vs诊断工具方案四:使用工具VLD(Visio Leak Detector)方案五Cppcheck内存泄漏 内存泄漏:指的是在程序里动态申请的内存在使…...
![](https://img-blog.csdnimg.cn/5bc78713193645f78b39580d90381dd8.jpeg#pic_center)
【贪心算法】一文让你学会“贪心”(贪心算法详解及经典案例)
文章目录前言如何理解“贪心算法”?贪心算法实战分析1.分糖果2.钱币找零3.区间覆盖内容小结最后说一句🐱🐉作者简介:大家好,我是黑洞晓威,一名大二学生,希望和大家一起进步。 👿本…...
![](https://img-blog.csdnimg.cn/4388369dffe648eb857d99d391e9eaeb.png#pic_center)
【字体图标iconfont】字体图标部署流程+项目源码分析
今日,心情甚是烦闷,原由… 公司项目需要将字体图标做一些细微的调整,我一人分析了许久,看不大懂源码的逻辑,产生了自我怀疑。深吸一口气,重新鼓起勇气,调整心境,一下子豁然开朗&…...
![](https://img-blog.csdnimg.cn/0f4184b8dd76462198fe995e491f423f.gif)
2023最全的Web自动化测试介绍(建议收藏)
做测试的同学们都了解,做Web自动化,我们主要用Selenium或者是QTP。 有的人可能就会说,我没这个Java基础,没有Selenium基础,能行吗?测试虽然属于计算机行业,但其实并不需要太深入的编程知识&…...
![](https://img-blog.csdnimg.cn/7fc0b9a951f7402c8bb657effc8a1a9e.png)
jvm_根节点枚举安全点安全区域
1、可达性分析可以分成两个阶段 根节点枚举 从根节点开始遍历对象图 前文我们在介绍垃圾收集算法的时候,简单提到过:标记-整理算法(Mark-Compact)中的移动存活对象操作是一种极为负重的操作,必须全程暂停用户应用程序才能进行,像这…...
![](https://img-blog.csdnimg.cn/img_convert/3ec84d5d3aa8ad1cd621ca05553e64db.png)
fabric(token-erc-20链码部署)
确保自己已经安装了fabric。没有安装的可以参考我之前的教程fabric中bootstrap.sh到底帮助我们干了什么?(手动执行相关操作安装fabric2.4)_./bootstrap.sh_小小小小关同学的博客-CSDN博客小伙伴们在跟着官方示例来安装fabric的时候都是相当烦…...
![](https://img-blog.csdnimg.cn/02689322e950416db1816be432f7b284.png)
C语言基础——流程控制语句
文章目录一、流程控制语句 -- 控制程序的运行过程 9条(一)、条件选择流程控制语句:if语句if……else……语句if……else if……语句switch语句(二)、循环流程控制语句:for语句while语句do while……语句co…...
![](https://img-blog.csdnimg.cn/6df947fa2672441fbeffad7ab236209f.gif)
WinForm | C# 界面弹出消息通知栏 (仿Win10系统通知栏)
ApeForms 弹出消息通知栏功能 文章目录ApeForms 弹出消息通知栏功能前言全局API通知栏起始方向通知排列方向通知栏之间的间隔距离无鼠标悬停时的不透明度消息通知窗体的默认大小示例代码文本消息提示栏文本消息提示栏(带选项)图文消息提示栏图文消息提示…...
![](https://img-blog.csdnimg.cn/f74590063ca84b7a89f85ec2e275e732.png)
刷题之最长公共/上升子序列问题
目录 一、最长公共子序列问题(LCS) 1、题目 2、题目解读 编辑 3、代码 四、多写一题 五、应用 二、最长上升子序列问题(LIS) 1、题目 2、题目解读 3、代码 四、多写一道 Ⅰ、题目解读 Ⅱ、代码 一、最长公共子序列问题&…...
![](https://img-blog.csdnimg.cn/img_convert/964d5c594e4c6ccea737be3c6b6bed4e.gif#pic_center)
【数据结构】千字深入浅出讲解栈(附原码 | 超详解)
🚀write in front🚀 📝个人主页:认真写博客的夏目浅石. 🎁欢迎各位→点赞👍 收藏⭐️ 留言📝 📣系列专栏:C语言实现数据结构 💬总结:希望你看完…...
![](https://www.ngui.cc/images/no-images.jpg)
自动驾驶V2X
1 SoC MDM9250 2 设备网络节点 mhi_swip0 rmnet_mhi0 3 网络协议栈log打印控制 include/linux/netdevice.h ethtool -s eth0 msglvl [level] ethtool -s eth0 msglvl 0x6001 4 URLs MHI initial design review https://lore.kernel.org/lkml/001601d52148$bd852840$388f78c0$c…...
![](https://img-blog.csdnimg.cn/cc9765dc19e34393bfec40e2103d80b9.png)
零基础自学网络安全/渗透测试有哪些常见误区?
一、网络安全学习的误区 1.不要试图以编程为基础去学习网络安全 不要以编程为基础再开始学习网络安全,一般来说,学习编程不但学习周期长,且过渡到网络安全用到编程的用到的编程的关键点不多。一般人如果想要把编程学好再开始学习网络安全往…...
![](https://img-blog.csdnimg.cn/b65225faa2174bf9ba5c6eede6aebe83.png)
ConvMixer:Patches Are All You Need
Patches Are All You Need 发表时间:[Submitted on 24 Jan 2022]; 发表期刊/会议:Computer Vision and Pattern Recognition; 论文地址:https://arxiv.org/abs/2201.09792; 代码地址:https:…...
![](https://www.ngui.cc/images/no-images.jpg)
day10—编程题
文章目录1.第一题1.1题目1.2思路1.3解题2.第二题2.1题目2.2涉及的相关知识2.3思路2.4解题1.第一题 1.1题目 描述: 给定一个二维数组board,代表棋盘,其中元素为1的代表是当前玩家的棋子,0表示没有棋子,-1代表是对方玩…...
![](https://img-blog.csdnimg.cn/img_convert/b90dd3f653a84ea9abc3a3dabb17472b.png)
如何测量锂电池的电量
锂电池在放电时我们有时需要知道电池的实时电量,如电池电量低了我们就需要及时给锂电池充电,避免电池过度放电。我手里的这个就是个单节锂电池电量显示模块,只需要将这个模块接到锂电池的正负极即可显示电量。这个模块的电量分为四档…...
![](https://img-blog.csdnimg.cn/img_convert/87c3c944ec1f35d91dcdf45f9d6427d3.gif)
优秀个人网站图片/推广技术
第一款面向大众的java版的视频管理系统。妖气山视频管理系统理论上可以制作任何类型的视频网站。源码地址:源码下载地址: https://gitee.com/javaex/yaoqishan下面是mysql版本: https://github.com/user-xiangpeng/yaoqishan软件架构前端:javaex后端&…...
定制网站建设设计公司/seo系统培训班
什么是箱型图 箱形图(Box-plot)又称为盒须图、盒式图或箱线图,是一种用作显示一组数据分散情况资料的统计图。因形状如箱子而得名。在各种领域也经常被使用,常见于品质管理。(来源:百度百科【箱型图】词条&…...
![](https://img-blog.csdnimg.cn/img_convert/b6f9d17e543bea3effbef9cd00f2ac57.png)
网站公司简介模板/河南百度推广公司
一、了解机器连接数情况问题:1.2.3.4的sshd的监听端口是22,如何统计1.2.3.4的sshd服务各种连接状态(TIME_WAIT/ CLOSE_WAIT/ ESTABLISHED)的连接数。常见方法:netstat -n | grep 1.2.3.4:22 | awk /^tcp/ {S[$NF]} END {for(a in S) print a,…...
![](https://img-blog.csdnimg.cn/img_convert/114f32a787a47fc5c6b9e8410b78aa41.png)
购物网站支付功能怎么做/在线网页制作
今天和大家分享一个能在手机上演示的高保真移动端元件库。 43页完整版案例(含页面跳转交互)预览地址:https://axhub.im/ax9/bace41c00c111653/#g1 135页元件库(只含单页交互)预览地址:https://axhub.im/a…...
![](/images/no-images.jpg)
it运维外包服务方案/seo网站排名优化快速排
一、接口测试的本质 :只是做了数据传递 二、接口测试的核心含义 :能够把请求发出去,然后接收的响应结果,结束是否达到我们的预期 三、Jmeter进行接口测试的固定流程 1.用工具创建HTTP请求 2.用工具发出请求 3.校验数据ÿ…...
![](/images/no-images.jpg)
网站吸流量/站长工具网站测速
在当前的大环境里,实体店产品同质化非常严重。经过一条商业街,我们会明显发现,同行业的几家店铺不管是产品类型、装修风格还是产品价格都十分相似,给人的感觉就是把相同的产品放在不同的店里。 这个时候,优秀的营销策…...