基于ffmpeg与SDL的视频播放库

        由于工作需要,自己封装的基于ffmpeg的视频编解码库,显示采用了SDL库。可以播放本地文件或网络流,支持多端口播放,支持文字叠加,截图、视频录制等等。

头文件代码:

#pragma once
#ifdef __DLLEXPORT
#define __DLL_EXP _declspec(dllexport)    
#else
#define __DLL_EXP _declspec(dllimport)    
#endif #include <stdio.h>
#include <string>using namespace std;
//录像状态
enum RecordStatus
{Idle,Recording,Stop
};//视频存储格式
enum VideoFormat
{MP4,AVI,
};//图片存储格式
enum PictureFormat
{JPEG,PNG,BMP,
};//播放器状态
enum PlayStatus
{Close,Playing,Pause
};//滤镜种类
enum FilterType
{Time,Reticle,Text,Other
};//颜色
struct RGBAColor
{BYTE R;BYTE G;BYTE B;BYTE A;
};//OSD字体属性结构体struct OSDParameter
{char* text;int fontSize;        //汉字字号int fontFamily;      //0=黑体,1=楷体,2=宋体 3:ArialRGBAColor fontColor;      //字体颜色 rgb表示RGBAColor backColor;      //字体背景色 rgb表示float x;             //字体坐标 x:宽度百分比0-1float y;             //字体坐标 y:高度百分比0-1bool visible;        //是否可见
};//格式enum  FrameFormat{AUDIO16,RGB32,YV12,UVVY,YUVJ420P};struct FrameInfo
{int width;  					   	//画面宽,单位像素。如果是音频数据则为0;int height; 					  	//画面高。如果是音频数据则为0;int stamp;  					  	//时标信息,单位毫秒。FrameFormat format;                 //数据类型,0:AUDIO16,1:RGB32,2:(YUV420P)YV12,3:YUVJ420P int frameRate; 					    //实时帧率。
};/**
* 功能描述:打开视频
* @param nPort:播放通道号[0,31] 
* @param url:视频文件或视频流地址
* @param data:图像控件句柄,后台录制时,赋值NULL
*
* @return 成功/失败
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_OpenVideo(int nPort, const char* url, const void* hWnd);/**
*  功能描述: 开始播放
* @param nPort:播放通道号[0,31]
* @param isRealTimePlay:实时播放,在需要实时播放时开启,如播放摄像头流。为false时,将按照帧率播放。
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_StartPlay(int nPort,bool isRealTimePlay);/**
*  功能描述: 暂停播放
* @param nPort:播放通道号[0,31] 
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_PausePlay(int nPort);/**
* 功能描述:关闭视频释放资源
* @param nPort:播放通道号[0,31] 
*/
extern "C" __declspec(dllexport)  bool _stdcall VideoPlayer_CloseVideo(int nPort);/**
* 功能描述:设置文件播放指针的相对位置(百分比)
* @param nPort:播放通道号[0,31] 
* @param pos:播放时间位置  0-100
* @param fReleatePos:0-100
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_SetPlayPos(int nPort, float fReleatePos);/**
* 功能描述:播放速度控制
* @param nPort:播放通道号[0,31] 
* @param speed:速度  0:正常播放   1:1.25倍速  2:1.5倍速 3:1.75倍速 4:2倍速  5:0.75倍速  6:0.5倍速 7:0.25倍速
*/
extern "C" __declspec(dllexport) void _stdcall VideoPlayer_ChangeSpeed(int nPort, int speed);/**
* 功能描述:获取当前播放时间
* @param nPort:播放通道号[0,31] 
* @return 播放时间  单位:秒
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_GetPlayedTime(int nPort);/**
* 功能描述:播放窗口缩放
* @param nPort:播放通道号[0,31] 
* @return 成功/失败
*/
extern "C" __declspec(dllexport)  bool _stdcall VideoPlayer_ResizeWindow(int nPort);/**
* 功能描述:设置录制参数
* @param nPort:播放通道号[0,31]
* @param fps:视频帧率
* @param quality:图像质量(0-10) 越高质量越好,占用内存越大,设置为0时,为自动码率
* @param duration:单个文件时长(min),默认60分钟
* @param frameExtractionMode:抽帧模式 0:不抽帧,以fps进行编码;1:1/2 帧率,以fps/2进行抽帧(保证fps/2为整数,否则会出现丢帧情况)
* @param format:存储格式,默认为mp4
*
* @return 成功/失败
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_SetRecordParameter(int nPort,int fps, float quality = 5, int duration = 60, int frameExtractionMode = 0, VideoFormat format= VideoFormat::MP4);/**
* 功能描述:开始录制
* @param nPort:播放通道号[0,31]
* @param path:录像保存路径包含文件名
*
* @return 成功/失败
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_StartRecord(int nPort, const char* path);/**
* 功能描述:结束录制
* @param nPort:播放通道号[0,31] 
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_StopRecord(int nPort);/**
* 功能描述:视频截图
* @param nPort:播放通道号[0,31]
* @param path: 图像保存的路径,不含后缀名
* @param format:图像格式,默认为jpeg
*
* @return 成功/失败
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_ShotImage(int nPort, const char* path, PictureFormat format= PictureFormat::JPEG);/**
* 功能描述:设置某一行的OSD叠加文本
* @param nPort:播放通道号[0,31] 
* @param osdID:OSD文本序号
* @param para:osd属性
*
* @return 成功/失败
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_SetOSDText(int nPort, int osdID, OSDParameter osdParam);/**
* 功能描述:设置所有的OSD文本(总共20行)
* @param nPort:播放通道号[0,31]
* @param para:osd属性
*
* @return 成功/失败
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_SetAllOSDTexts(int nPort, OSDParameter osdParams[]);/**
* 功能描述:清除所有OSD文本
* @param nPort:播放通道号[0,31] 
*
* @return 成功/失败
*/
extern "C" __declspec(dllexport) bool _stdcall VideoPlayer_ClearOSDText(int nPort);/**
* 功能描述:设置解码缓存队列大小
* @param nPort:播放通道号[0,31]
* @param size:默认为10,设置过小会丢帧,设置过大可能会导致画面延迟
*
* @return 成功/失败
*/
extern "C" __declspec(dllexport) void _stdcall VideoPlayer_SetDecodedBufferSize(int nPort, int size);/**
* 功能描述:单帧往后播放 
* @param nPort:播放通道号[0,31]
*/
extern "C" __declspec(dllexport) bool  _stdcall VideoPlayer_NextFrame(int nPort);/**
* 功能描述:单帧往前播放 
* @param nPort:播放通道号[0,31]
*/
extern "C" __declspec(dllexport) bool  _stdcall VideoPlayer_PrevFrame(int nPort);/**
* 功能描述:跳转视频到某一时间位置 
* @param nPort:播放通道号[0,31]
* @param pos:视频位置百分比
*/
extern "C" __declspec(dllexport) bool  _stdcall VideoPlayer_SetPlayPos(int nPort,float pos);/**
* 功能描述:显示/隐藏当前系统时间
* @param nPort:播放通道号[0,31]
* @param visible:是否显示
* @param xPos:坐标位置X,宽度百分比
* @param yPos:坐标位置Y,高度百分比
* @param fontSize:字体大小,默认50
*/
extern "C" __declspec(dllexport) bool  _stdcall VideoPlayer_SetDateTime(int nPort,bool visible, float xPos, float yPos,int fontSize=50);/**
* 功能描述:当前解码完成数据回调
* @param nPort:播放通道号[0,31]
* @param pBuf:yuv数据指针
* @param nSize:数据大小
* @param pFrameInfo:帧信息
*/
typedef void(_stdcall* DecodeCallBack)(int nPort, const unsigned char* pBuf, int nSize, FrameInfo& pFrameInfo);/**
* 功能描述:设置解码回调函数
* @param nPort:播放通道号[0,31]
* @param pDecodeProc:回调函数
*/
extern "C" __declspec(dllexport) bool  _stdcall VideoPlayer_SetDecCallBack(int nPort, DecodeCallBack pDecodeProc);/**
* 功能描述:在显示句柄窗口中绘制文本、图形等
* @param nPort:播放通道号[0,31]
* @param hWnd:视频窗口句柄,用于创建GDI
* @param width:视频窗口宽度
* @param height:视频窗口高度
*/
typedef void(_stdcall* DrawCallBack)(int nPort, const void* hWnd,int width,int height);extern "C" __declspec(dllexport) bool  _stdcall VideoPlayer_SetDrawCallBack(int nPort, DrawCallBack pDrawProc);

 库支持C++,C#调用,以下是C#调用的方法:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using VideoPlayDemo.Onvif;
using static VideoPlayDemo.MYVideoPlay;namespace VideoPlayDemo
{public partial class Form1 : Form{const int PLAY_PORT1 = 0;const int PLAY_PORT2 = 1;public event MYVideoPlay.DecodeCallBack decodeCallBack;public event MYVideoPlay.DrawCallBack drawCallBack;bool[] isRecording = new bool[2];bool[] isOpened = new bool[2];MYVideoPlay.OSDParameter[] OSDParameters1 = new MYVideoPlay.OSDParameter[20];MYVideoPlay.OSDParameter[] OSDParameters2 = new MYVideoPlay.OSDParameter[20];public Form1(){InitializeComponent();Timer timer = new Timer();timer.Interval = 100;timer.Enabled = true;timer.Tick += Timer_Tick;decodeCallBack += new MYVideoPlay.DecodeCallBack(Form1_decodeCallBack);drawCallBack += new MYVideoPlay.DrawCallBack(Form1_drawCallBack);//初始化for (int i = 0; i < 20; i++){OSDParameters1[i] = new MYVideoPlay.OSDParameter();OSDParameters1[i].visible = false;OSDParameters1[i].text = "test中文"+i.ToString();OSDParameters1[i].fontSize = 100;OSDParameters1[i].fontFamily = 0;OSDParameters1[i].fontColor = new MYVideoPlay.RGBAColor(Color.White);OSDParameters1[i].backColor = new MYVideoPlay.RGBAColor(Color.Transparent);OSDParameters2[i] = new MYVideoPlay.OSDParameter();OSDParameters2[i].visible = false;OSDParameters2[i].text = "test中文" + i.ToString();OSDParameters2[i].fontSize = 100;OSDParameters2[i].fontFamily = 0;OSDParameters2[i].fontColor = new MYVideoPlay.RGBAColor(Color.Yellow);OSDParameters2[i].backColor = new MYVideoPlay.RGBAColor(Color.Transparent);}}#region 视频播放控制方法/// <summary>/// 打开视频/// </summary>/// <param name="port"></param>public bool OpenVideo(int port,string url,IntPtr intPtr){bool ret = false;ret = MYVideoPlay.VideoPlayer_SetDecCallBack(port, decodeCallBack);if (!ret){MessageBox.Show("设置解码回调函数失败!");return ret;}ret = MYVideoPlay.VideoPlayer_SetDrawCallBack(port, drawCallBack);if (!ret){MessageBox.Show("设置绘图回调函数失败!");return ret;}ret = MYVideoPlay.VideoPlayer_OpenVideo(port, url, intPtr);if (!ret){MessageBox.Show("打开视频失败!");return ret;}ret = MYVideoPlay.VideoPlayer_StartPlay(port,false);if (!ret){MessageBox.Show("播放失败!");return ret;}//叠加时间        //     ret = MYVideoPlay.VideoPlayer_SetDateTime(port, true, 0.01f, 0.01f,70);return ret;}/// <summary>/// 关闭视频/// </summary>/// <param name="port"></param>private bool CloseVideo(int port){return MYVideoPlay.VideoPlayer_CloseVideo(port);}/// <summary>/// 开始录制  帧率60/// </summary>/// <param name="port"></param>/// <param name="halfRate"></param>private bool StartRecord(int port,bool halfRate){bool ret = false;if(halfRate)ret = MYVideoPlay.VideoPlayer_SetRecordParameter(port, 60, 5, 60,1);elseret = MYVideoPlay.VideoPlayer_SetRecordParameter(port, 60, 5, 60, 0);string path = string.Format("d:\\video_{0}", port);ret = MYVideoPlay.VideoPlayer_StartRecord(port, path);if (!ret)MessageBox.Show("开启录制失败!");return ret;}/// <summary>/// 停止录制/// </summary>/// <param name="port"></param>private bool StopRecord(int port){bool ret = MYVideoPlay.VideoPlayer_StopRecord(port);return ret;}/// <summary>/// 截图/// </summary>/// <param name="port"></param>/// <returns></returns>private bool ShotImage(int port){bool ret = MYVideoPlay.VideoPlayer_ShotImage(port, "d:\\" + port.ToString(), MYVideoPlay.PictureFormat.JPEG);return ret;}int[] frameRates = new int[4];private void Form1_decodeCallBack(int nPort, IntPtr pBuf, int nSize, ref MYVideoPlay.FrameInfo pFrameInfo){frameRates[nPort] = pFrameInfo.frameRate;this.Invoke((Action)delegate{this.lbFPS1.Text = frameRates[0].ToString()+"fps";this.lbFPS2.Text = frameRates[1].ToString()+"fps";});}private void Form1_drawCallBack(int nPort, IntPtr hWnd, int width, int height){}#endregion/// <summary>/// 打开视频/// </summary>/// <param name="sender"></param>/// <param name="e"></param>private void btnOpenVideo_Click(object sender, EventArgs e){Button btn = sender as Button;int n = int.Parse(btn.Tag.ToString());if (isOpened[n])return;string url="";IntPtr intPtr= IntPtr.Zero;switch (n){case 0: url = textBox1.Text;intPtr = pnlVideo1.Handle; break;case 1: url = textBox2.Text;intPtr = pnlVideo2.Handle; break;}Task task = new Task(() =>{//网络直播流(非相机流)时设置更大的buffer进行缓存,否则出现马赛克MYVideoPlay.VideoPlayer_SetDecodedBufferSize(n, 250);isOpened[n] = OpenVideo(n,url,intPtr);});task.Start();}/// <summary>/// 关闭视频/// </summary>/// <param name="sender"></param>/// <param name="e"></param>private void btnCloseVideo_Click(object sender, EventArgs e){Button btn = sender as Button;int n = int.Parse(btn.Tag.ToString());if (!isOpened[n])return;bool ret = CloseVideo(n);isOpened[n] = !ret;}/// <summary>/// 开始录制/// </summary>/// <param name="sender"></param>/// <param name="e"></param>private void btnStartRecord_Click(object sender, EventArgs e){Button btn = sender as Button;int n = int.Parse(btn.Tag.ToString());if (isRecording[n] || !isOpened[n])return;if (n == 0)isRecording[n] = StartRecord(n, true);elseisRecording[n] = StartRecord(n, false);}/// <summary>/// 停止录制/// </summary>/// <param name="sender"></param>/// <param name="e"></param>private void btnStopRecord_Click(object sender, EventArgs e){Button btn = sender as Button;int n = int.Parse(btn.Tag.ToString());if (!isRecording[n] || !isOpened[n])return;bool ret = StopRecord(n);isRecording[n] = !ret;}/// <summary>/// 截图/// </summary>/// <param name="sender"></param>/// <param name="e"></param>private void btnShotImage_Click(object sender, EventArgs e){Button btn = sender as Button;int n = int.Parse(btn.Tag.ToString());ShotImage(n);}/// <summary>/// 叠加字符测试/// </summary>/// <param name="sender"></param>/// <param name="e"></param>private void Timer_Tick(object sender, EventArgs e){Random rd = new Random();bool ret = false;if (isOpened[PLAY_PORT1]){OSDParameters1[0].visible = OSDParameters1[1].visible = true;OSDParameters1[0].x = (float)rd.NextDouble();OSDParameters1[0].y = (float)rd.NextDouble();OSDParameters1[1].x = (float)rd.NextDouble();OSDParameters1[1].y = (float)rd.NextDouble();//ZYVideoPlay.VideoPlayer_SetAllOSDTexts(PLAY_PORT1, OSDParameters1);}if (isOpened[PLAY_PORT2]){OSDParameters2[0].visible = OSDParameters2[1].visible = true;OSDParameters2[0].x = (float)rd.NextDouble();OSDParameters2[0].y = (float)rd.NextDouble();OSDParameters2[1].x = (float)rd.NextDouble();OSDParameters2[1].y = (float)rd.NextDouble();//   ret = ZYVideoPlay.VideoPlayer_SetAllOSDTexts(PLAY_PORT2, OSDParameters2);}}private void timer1_Tick(object sender, EventArgs e){if (isRecording[PLAY_PORT1]){if (DateTime.Now.Millisecond < 500)lbRec1.Visible = true;elselbRec1.Visible = false;}elselbRec1.Visible = false;if (isRecording[PLAY_PORT2]){if (DateTime.Now.Millisecond < 500)lbRec2.Visible = true;elselbRec2.Visible = false;}elselbRec2.Visible = false;}private void Form1_FormClosing(object sender, FormClosingEventArgs e){for(int i=0;i<2;i++){if (isOpened[i])CloseVideo(i);}}}
}

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

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

相关文章

如何用正确的姿势监听Android屏幕旋转

作者&#xff1a;37手游移动客户端团队 背景 关于个人&#xff0c;前段时间由于业务太忙&#xff0c;所以一直没有来得及思考并且沉淀点东西&#xff1b;同时组内一个个都在业务上能有自己的思考和总结&#xff0c;在这样的氛围下&#xff0c;不由自主的驱使周末开始写点东西&…

antv/l7地图,鼠标滚动,页面正常滑动-- 我们忽略的deltaY

背景 在官网项目中&#xff0c;需要使用一个地图&#xff0c;展示产品的分布区域及数量。希望的交互是&#xff0c;鼠标放上标点&#xff0c;tooltip展示地点和数量等信息。鼠标滚动&#xff0c;则页面随着滚动。但是鼠标事件是被地图代理了的&#xff0c;鼠标滚动意味着地图的…

【vue3】基础知识点-computed和watch

学习vue3&#xff0c;都会从基础知识点学起。了解setup函数&#xff0c;ref&#xff0c;recative&#xff0c;watch、computed、pinia等如何使用 今天说vue3组合式api&#xff0c;computed和watch 在vue3中&#xff0c;computed和watch仍然是非常有用的特性&#xff0c;帮助处…

JavaWeb学习|JSP相关内容

1.什么是JSP Java Server Pages: Java服务器端页面&#xff0c;也和Servlet一样&#xff0c;用于动态Web技术! 最大的特点: 。写JSP就像在写HTML 。区别: 。HTML只给用户提供静态的数据 。JSP页面中可以嵌入JAVA代码&#xff0c;为用户提供动态数据 JSP最终也会被转换成为一…

Android数据存储选项:SQLite、Room等

Android数据存储选项&#xff1a;SQLite、Room等 1. 引言 在移动应用的开发过程中&#xff0c;数据存储是至关重要的一环。无论是用户的个人信息、设置配置还是应用产生的临时数据&#xff0c;都需要在设备上进行存储以便随时访问。随着移动应用的日益发展&#xff0c;数据存…

springboot-mybatis的增删改查

目录 一、准备工作 二、常用配置 三、尝试 四、增删改查 1、增加 2、删除 3、修改 4、查询 五、XML的映射方法 一、准备工作 实施前的准备工作&#xff1a; 准备数据库表 创建一个新的springboot工程&#xff0c;选择引入对应的起步依赖&#xff08;mybatis、mysql驱动…

Flowable-网关-事件网关

目录 定义图形标记XML内容使用示例视频教程 定义 通常网关根据连线条件来决定后继路径&#xff0c;但事件网关不同&#xff0c;它提供了根据事件做选择的方式。 事件网关的每个外出顺序流都需要连接至一个捕获中间事件。当流程执行到达事件网关时&#xff0c;网关类 似处于等待…

【阻止IE强制跳转到Edge浏览器】

由于微软开始限制用户使用Internet Explorer浏览网站&#xff0c;IE浏览器打开一些网页时会自动跳转到新版Edge浏览器&#xff0c;那应该怎么禁止跳转呢&#xff1f; 1、点击电脑左下角的“搜索框”或者按一下windows键。 2、输入“internet”&#xff0c;点击【Internet选项…

Python Opencv实践 - 在图像上绘制图形

import cv2 as cv import numpy as np import matplotlib.pyplot as pltimg cv.imread("../SampleImages/pomeranian.png") print(img.shape)plt.imshow(img[:,:,::-1])#画直线 #cv.line(img,start,end,color,thickness) #参考资料&#xff1a;https://blog.csdn.ne…

百度智能云“千帆大模型平台”最新升级:接入Llama 2等33个模型!

今年3月&#xff0c;百度智能云推出“千帆大模型平台”。作为全球首个一站式的企业级大模型平台&#xff0c;千帆不但提供包括文心一言在内的大模型服务及第三方大模型服务&#xff0c;还提供大模型开发和应用的整套工具链&#xff0c;能够帮助企业解决大模型开发和应用过程中的…

04-2_Qt 5.9 C++开发指南_SpinBox使用

文章目录 1. SpinBox简介2. SpinBox使用2.1 可视化UI设计2.2 widget.h2.3 widget.cpp 1. SpinBox简介 QSpinBox 用于整数的显示和输入&#xff0c;一般显示十进制数&#xff0c;也可以显示二进制、十六进制的数&#xff0c;而且可以在显示框中增加前缀或后缀。 QDoubleSpinBox…

stl_list类(使用+实现)(C++)

list 一、list-简单介绍二、list的常用接口1.常见构造2.iterator的使用3.Capacity和Element access4.Modifiers5.list的迭代器失效 三、list实现四、vector 和 list 对比五、迭代器1.迭代器的实现2.迭代器的分类&#xff08;按照功能分类&#xff09;3.反向迭代器(1)、包装逻辑…

嵌入式开发学习(STC51-9-led点阵)

内容 点亮一个点&#xff1b; 显示数字&#xff1b; 显示图像&#xff1b; LED点阵简介 LED 点阵是由发光二极管排列组成的显示器件 通常应用较多的是8 * 8点阵&#xff0c;然后使用多个8 * 8点阵可组成不同分辨率的LED点阵显示屏&#xff0c;比如16 * 16点阵可以使用4个8 *…

【Linux命令详解 | less命令】Linux系统中用于分页显示文件内容的命令

文章标题 简介一&#xff0c;参数列表二&#xff0c;使用介绍1. 分页显示文件内容2. 搜索关键词3. 显示行号4. 显示特定内容5. 只显示匹配行6. 忽略大小写搜索7. 输出到文件8. 动态查看文件增长9. 开启对二进制文件的支持10. 显示控制字符11. 忽略键盘输入12. 显示百分比进度条…

001-Spring boot 启动内置Web容器分析

目录 代码入口上下文容器 加载web容器 代码入口 上下文容器 SpringApplication.run(App.class); //追踪下去发现 context createApplicationContext();createApplicationContext()&#xff1a; return this.applicationContextFactory.create(this.webApplicationType);这里…

python 封装sql 增删改查连接MySQL

select * from Teacher limit 10 连接字符串配置MysqlConfig.py class MysqlConfig:HOST 192.168.56.210PORT 3306USER rootPASSWORD 1qaz0987654321DBStudentDBCHARSET utf8封装增删改查MysqlConnection.py Author: tkhywang 2810248865qq.com Date: 2023-06-19 15:44:48 Las…

使用MIT Kerberos Ticket Manager在windows下浏览器访问hadoop页面

Author : Spinach | GHB Link : http://blog.csdn.net/bocai8058文章目录 前言准备配置说明安装Firefox浏览器安装MIT Kerberos Ticket Manager客户端配置krb5.ini文件配置MIT Kerberos Ticket Manager客户端配置Firefox浏览器代理参数 访问WebUI 前言 kerberos是一种计算机…

linux 查看磁盘大小 内存 目录下各目录大小

查看当前服务器挂在的磁盘大小及已使用、可使用、使用占比、磁盘对应的目录等 df -TH 查看当前目录下 各子目录或文件的大小&#xff1a;右边是目录或文件名&#xff0c;左边是占用的大小 du -sh * 使用 rm命令删除目录或文件&#xff1a;删了数据找不回来&#xff0c;&#x…

【二叉树】105. 从前序与中序遍历序列构造二叉树

链接: 105. 从前序与中序遍历序列构造二叉树 先序 能够确定谁是根 中序 知道根之后&#xff0c;能够确定左子树和右子树的范围 例子 根据先序的性质&#xff08;根左右&#xff09;&#xff0c;能够确定根&#xff0c;我们就能够从总序中找出根节点&#xff08;rooti所在…

MyBatis简介及环境配置

文章目录 一、什么是MyBatis二、MyBatis开发环境配置1.创建数据库表2.添加MyBatis框架支持3.配置连接字符串和MyBatis4.添加业务代码流程 一、什么是MyBatis MyBatis是一种持久层框架&#xff0c;也是一种ORM框架&#xff08;Object Relational Mapping即对象关系映射&#xf…