C#.Net筑基-类型系统②常见类型

news2025/2/28 3:09:17

image.png

01、结构体类型Struct

结构体 struct 是一种用户自定义的值类型,常用于定义一些简单(轻量)的数据结构。对于一些局部使用的数据结构,优先使用结构体,效率要高很多。

  • 可以有构造函数,也可以没有。因此初始化时可以new,也可以用默认default。但当给字段设置了初始值时,则必须有显示的构造函数。
  • 结构体中可以定义字段、属性、方法,不能使用终结器。
  • 结构体可继承接口,并实现接口,但不能继承其他类、结构体。
  • 结构体是值类型,被分配在栈上面,因此在参数传递时为值传递。

⁉️结构体始终都是分配在栈上吗?—— 不一定,当结构体是类的成员时,则会随对象一起分配在堆上。同时当结构体上有引用类型字段时,该字段只存储引用对象的地址,引用对象还是分配在堆上。

void Main()
{
	Point p1 = default;
	//Point p1 = default(Point);
	Point p2 = new Point(1, 2);
	p1.X = 100;
	p2.X = 100;
}
public struct Point
{
	public int X;
	public int Y;

	public Point(int x, int y)
	{
		X = x;
		Y = y;
	}
}

1.1、只读结构体与只读函数

readonly struct申明一个只读的结构体,其所有字段、属性都必须是只读的。

public readonly struct Point
{
	public readonly int X,Y;
}

用在方法上,该方法中不可修改任何字段值。这只能用在结构体中,结构体不能继承,不知道这个特性有什么用?

public struct Point
{
	public int X;
	public int Y;

	public readonly int GetValue()
	{
		X--;   //Error:不可修改
		return X + Y;
	}
}

1.2、Ref 结构体

ref 结构类型 用ref struct申明,该结构体只能存储在栈上,因此任何会导致其分配到堆上的行为都不支持,如装箱、拆箱,作为类的成员等都不支持。
Ref 结构体 可用于一些高性能场景,System.Span、ReadOnlySpan 都是 readonly ref struct结构体。

public ref struct Point
{
	public int X,Y;
}

02、枚举Enum

枚举类型 是由基础值类型(byte、int、long等)组成的一组命名常量的值类型,用enum来申明定义。常用于一些有固定值的类别申明,如性别、方向、数据类型等。

  • 枚举成员默认是int,可以修改为其他整数类型,如byteshortuintlong等。
  • 枚举项可设置值,也可省略,或者部分设置值。值默认是从0开始,并按顺序依次递增。
  • 枚举变量的默认值始终是0
  • 枚举本质上就是命名常量,因此可以与值类型进行相互转换(强制转换)。
  • 特性Description常用来定义枚项在UI上的显示内容,使用反射获取。
public enum UserType : int  //常量类型,可以修改为其他整数类型
{
    [Description("普通会员")]
	Default,
	VIP = 10,
	SupperVIP,  //继续前一个,值为11
}
void Main()
{
	var t1 = UserType.Default;
	Console.WriteLine(t1.ToString()); //输出名称:Default
	Console.WriteLine((int)t1);       //输出值:0
    Console.WriteLine($"{t1:F}");     //输出名称:Default
	Console.WriteLine($"{t1:D}");     //输出值:0
	var t2 = (UserType)0;
	int t3 = (int)UserType.Default;
	Console.WriteLine(t1 == t2); //True
}

2.1、Enum 类API

System.Enum 类型是所有枚举类型的抽象基类,提供了一些API方法用于枚举的操作,基本都是静态方法。Enum 类型还可以作为泛型约束使用。

🔸静态成员说明
HasFlag(Enum)判断(位域)枚举是否包含一个枚举值,返回bool
🔸静态成员说明
GetName<TEnum>(TEnum)获取枚举值的(常数)名称
GetNames<TEnum>()获取枚举定义的所有(常数)名称数组
GetValues<TEnum>()获取枚举定义的所有成员数组
IsDefined(Type, Object)判断给定的值(数值或名称)是否在枚举中定义
Parse<TEnum>(String)解析数值、名称为枚举,转换失败抛出异常
TryParse<TEnum>(String, TEnum)安全的转换,同上,转换结果通过out参数输出,返回bool表示是否转换成功
🔸其他说明
Type.IsEnumType的属性,用于判断一个类型是否枚举类型

2.2、位域Flags

枚举位域用[Flags]特性标记,从而可以使用枚举的位操作,实现多个枚举值合并的的能力。在有些多选值的场景很有用,用一个数值可表示多个内容,如QQ的各种钻(绿钻、红钻、黄钻…)用一个值就可以表示,参考下面代码示例。

  • 枚举定义时加上特性[Flags]
  • 要求枚举值必须是2的n次方,主要是各个成员的二进制值的对应位都不能一样,才能保障按位与、按位或运算的正确。
  • 合并值用按位或|,判断是否包含可以用按位与&,或者方法HasFlag(e)
  • 枚举类型命名一般建议用复数名词。
void Main()
{
	var t1 = QQDiamond.Green|QQDiamond.Red; //按位或运算,合并多个成员值
	Console.WriteLine((int)t1); //3,同时为绿钻、红钻
	//判断是否绿钻
	Console.WriteLine(t1.HasFlag(QQDiamond.Green)); //True
	//判断是否红钻,效果同上
	Console.WriteLine((t1 & QQDiamond.Red) == QQDiamond.Red); //True
}

[Flags]
public enum QQDiamond : sbyte
{
	None=0b0000,  //或者0
	[Description("绿钻")]
	Green=0b0001, //或者1
	Red=0b0010,   //或者2、1<<1
	Blue=0b0100,  //或者4、1<<2
	Yellow=0b1000,//或者8、1<<3
}

2.3、枚举值转换

枚举值为整形,枚举名称为string,因此常与int、string进行转换。

🔸转换为枚举说明
Enum.Parse()/TryParse()转换枚举值(字符串形式)、枚举名称为枚举对象,支持位域Flgas
TEnum(int)强制转换整形值为枚举,如果没有不会报错,支持位域Flgas
/Parse/TryParse方法解析
var t1 = Enum.Parse<QQDiamond>("3");     //Green
var t2 = Enum.Parse<QQDiamond>("Green"); //Green
//强转
QQDiamond t3 =(QQDiamond)56;
🔸枚举转换为string、int说明
ToString()获取枚举名称,支持位域Flgas
Enum.GetName(e)获取枚举名称,不支持位域Flgas
字符格式:G(或F)获取枚举名称,其中F主要用于Flgas枚举
强制类型转换:(int)TEnum获取枚举值
字符格式:D(或X)格式化中获取枚举值,D为十进制整形,X为16进制
//string
var s1 = qd.ToString();    //Green
var s2 = Enum.GetName(qd); //Green  不支持位于Flgas
var s3 = $"{qd:G}";        //Green
//int
var n1 = (int)qd;   //1
var n2 = $"{qd:D}"; //1

03、日期和时间的故事

在System命名空间中有 下面几个表示日期时间的类型:都是不可变的、结构体(Struct)

类型说明
DateTime常用的日期时间类型,默认使用的是本地时间(本地时区)
DateTimeOffset支持时区偏移量的的 DateTime,适合跨时区的场景。
TimeSpan表示一段时间的时间长度(间隔),或一天内的时间(类似时钟,无日期)
DateOnly 、 TimeOnly.NET 6 引入的只表示日期、时间,结构更简单轻量,适合特点场景
TimeZoneInfo时区,可表示世界上的任何时区

📢Ticks: 上面几个时间对象中都有一个 Ticks值,其值为从公元0001/01/01开始的计数周期。1 Tick (一个周期)为100纳秒(ns),0.1微秒(us),千万分之一秒,可以看做是C#中的最小时间单位。

Console.WriteLine(DateTime.Now.Ticks);            //638504277997063647
Console.WriteLine(DateTimeOffset.Now.Ticks);      //638504277997063874
Console.WriteLine(TimeSpan.FromSeconds(1).Ticks); //10000000

3.1、什么是UTC、GMT?

UTC(Coordinated Universal Time)世界标准时间(协调时间时间),简单理解就是 0时区的时间,是国际通用时间。它与0度经线的平太阳时相差不超过1秒,接近格林尼治标准时间(GMT)。

**格林尼治标准时间(Greenwich Mean Time,GMT)**是指位于伦敦郊区的皇家格林尼治天文台的标准时间,因为本初子午线被定义在通过那里的经线。 理论上来说,格林尼治标准时间的正午是指当太阳横穿格林尼治子午线时的时间。

📢 由于地球在它的椭圆轨道里的运动速度不均匀,因此GMT是不稳定的。而UTC时间是由原子钟提供的,更为精确可靠,基本上已经取代GMT标准了。

image.png

我们日常使用的DateTime.Now获取的时间其实是带了本地时区的(TimeZone),北京时区(+8小时),就是相比UTC时间,多了8个小时的偏差(时差)。DateTime 的Kind属性为DateTimeKind枚举,指定了时区类型:

  • Unspecified:不确定的,大部分场景会被认为是Local的。
  • Utc:UTC标准时区,偏移量为0。
  • Local(默认值):本地时区的时间,偏移量根据本地时区计算,如北京时间的偏移量为+8小时
public enum DateTimeKind
{
	Unspecified,
	Utc,
	Local
}

3.2、DateTime

🔸静态成员说明
Now、UtcNow当前本地时间、当前UTC时间,还有一个Today 只有日期部分的值
MinValue、MaxValue最小、最大值
UnixEpochUnix 0点的时间,值就是 1970 年 1 月 1 日的 00:00:00.0000000 UTC
Parse、ParseExact解析字符串转换为DateTime值,转换失败会抛出异常
TryParse、TryParseExact作用同上,安全版本的,Exact版本的方法可配置时间字符格式
🔸实例成员说明
Date只有日期部分的DateTime值
KindDateTimeKind 类型,默认Local,构造函数中可以指定
Ticks计时周期总数,单位为100ns(纳秒)
Year、Month、Day…当前时间的年、月、日、星期等等
🔸方法
Add***添加值后返回一个新的 DateTime,可以为负数
ToString(String)转换为字符串,指定日期时间格式,详细格式参考《String字符串全面了解》
ToUniversalTime()转换为UTC时间

3.3、DateTimeOffset

DateTimeOffset 和 DataTime 很像,使用、构造方式、API都差不多。主要的区别就是多了时区(偏移Offset),构造函数中可以用 TimeSpan 指定偏移量。DateTimeOffset 内部有两个比较重要的字段:

  • 用一个短整型 short _offsetMinutes 来存储时区偏移量(基于UTC),单位为分钟。
  • 用一个DateTime 存储始终为UTC的日期时间。
🔸静态成员说明
UtcTicks(UTC) 日期和时间的计时周期数
Offset时区偏移量,如北京时间:DateTimeOffset.Now.Offset //08:00:00
UtcDateTime返回本地UTC的DateTime
LocalDateTime返回本地时区的DateTime
DateTime返回Kind类型为Unspecified的DateTime,忽略了时区的DateTime值

image.png

用一个示例来理解DataTime、DataTimeOffset的区别: 比如你在一个跨国(跨时区)团队,你要发布一个通知:

  • “本周五下午5点前提交周报”,不同时区都是周五下午5点前提交报告,虽然他们不是同一时刻,此时可用DateTime
  • “明天下午5点开视频会”,此时则需要大家都在同一时刻上线远程会议,可能有些地方的是白天,有些则在黑夜,此时可用DateTimeOffset。

3.4、TimeSpan

TimeSpan 用来表示一段时间长度,最大值为1000W天,最小值为100纳秒。常用TimeSpan.From***()、构造函数、或DateTime的 差值结果 来构造。

TimeSpan t1 =TimeSpan.FromSeconds(12);  //00:00:12  //12秒
TimeSpan t2= new TimeSpan(12,0,0) - t1; //11:59:48  //11小时59分48秒
TimeSpan t3 = DateTime.Now.AddSeconds(12) - DateTime.Now; 00:00:12
var t4 = new TimeSpan(15,1,0,0); //15.01:00:00  //15天1小时
var t5= DateTime.Now.TimeOfDay;  //当天的时间

04、record是什么类型?

record 记录类型用来定义一个简单的、不可变(只读) 的数据结构,定义比较方便,常用于一些简单的数据传输场景。record 本质上就是定义一个class类型(也可申明为record struct结构体),因此语法上就是 类型申明+主构造函数的形式。

🚩 可以把 Record 看做是一个快速定义类(结构体)的语法糖,编译器会构建完整的类型。

  • 构造函数中的参数会生成公共的只读属性,其他自动生成的内容还包括EqualsToString、解构赋值等。
  • record 默认为class(可缺省),用record struct 则可申明为一个结构体的。
  • record 类型可以继承另一个record类型,或接口,但不能继承其他普通class
  • 支持使用with语句创建非破坏性副本。
public record Car(string Width);				//class
public record struct User(string Name, int Age);//struct
public record class Person(DateTime Birthday);  //class
void Main()
{
	var u1 = new User("sam",122);
	var u2 = new User("sam",122);
    u1.Age = 1; //只读,不可修改
	Console.WriteLine(u1 ==u2);                       //True
	Console.WriteLine(Object.ReferenceEquals(u1,u2)); //False
	var (name,_) = u1;       //解构赋值
	Console.WriteLine(name); //sam
}
public record Person2 //创建一个可更改的recored类型
{
	public string FirstName { get; set; }
	public string LastName { get; set; }
};

通过查看编译后的代码来了解recored的本质,下面是代码public record User(string Name, int Age)编译后生成的代码(简化后),完整代码可查看在线 sharplab代码。

  • 主构造函数中的参数都生成了只读属性,如果是struct结构体则属性是可读、可写的。
  • 生成了ToString() 方法,用stringBuilder 打印了所有字段名、字段值。
  • 生成了相等比较的方法、相等运算符重载,及GetHashCode(),相等比较会比较字段值。
  • 还生成了Deconstruct方法,用来支持解构赋值,var (name,age) = new User("sam",19);
public class User : IEquatable<User>
{
	public string Name{get;init;}
	public int Age{get;init;}
	public User(string Name, int Age)
	{
		this.Name = Name;
		this.Age = Age;
	}
	public override string ToString()
	{
		StringBuilder stringBuilder = new StringBuilder();
		//把所有字段名、值输出
		return stringBuilder.ToString();
	}
	public static bool operator !=(User left, User right)
	{
		return !(left == right);
	}
	public static bool operator ==(User left, User right)
	{...}
	public override int GetHashCode()
	{...}
	public virtual bool Equals(User other)
	{...}
    
	//支持解构赋值Deconstruct
	public void Deconstruct(out string Name, out int Age)
	{
		Name = this.Name;
		Age = this.Age;
	}
 }

record 申明可以用简化的语法(只有主构造函数,没有“身体”),也可以和class一样自定义一些内部成员。如下面示例中,自定义实现了ToString方法,则编译器就不会再生成该方法了,同时这里加了密封sealed标记,子类也就不能重写了。

void Main()
{
	var u = new User("John", 25);
	Console.WriteLine(u.ToString());
	u.SayHi();
}

public record User(string Name, int Age)
{
	public sealed override string ToString() => $"{Name} {Age}"; 

	public void SayHi() => Console.WriteLine($"Hi {Name}");
}

05、元祖Tuple

元祖 Tuple 其实就微软内置的一组包含若干个属性的泛型类型,包括结构体类型的 System.ValueTuple、引用类型的 System.Tuple,包含1到8个只读属性。

  • System.ValueTuple,是值类型,结构体,成员是字段,可修改。
  • System.Tuple 类型是引用类型,成员是只读属性。

image.png

📢 优先推荐使用 ValueTuple,这也是微软深度支持的,性能更好,默认类型推断用的都是ValueTuple。Tuple 作为历史的产物,在语言级别没有任何特殊支持。

下面代码为Tuple<T1>的源代码,就是这么朴实无华,其他就是相等比较、ToString、索引器。

public struct ValueTuple<T1, T2>
{
	public T1 Item1;
	public T2 Item2;
	public ValueTuple(T1 item1, T2 item2)
	{
		Item1 = item1;
		Item2 = item2;
	}
}

🚩C#在语法层面对ValueTuple的操作提供了很多便捷支持,让元祖的使用非常简单、优雅,基本可以替代匿名类型。

  • 简化 Tuplec 申明:用括号的简化语法,(Type,Type,...)(string,int)等效于ValueTuple<string,int>,编译器会进行类型推断。
  • 值相等:元祖内部实现了相等比较操作符重载,比较的是字段值。
  • 元素命名:元祖可以显示指定字段名称,比原来的无意义Item1、Item2好用多了。不过命名是开发态支持,编译后还是Item1、Item2,因此在运行时(反射)不可用。
  • 解构赋值,元祖对解构的支持是编译器行为。
ValueTuple<double,double> p1 = new (1,5);
//简化语法
(double, double) p2 = (3, 5.5);
var p3 = (3, 5.5); //类型推断,进一步简化
var dis = p2.Item1 * p2.Item2; //Item1、Item2 成员
//值比较
Console.WriteLine(p2 == p3); //True
//命名,有名字的元祖
var p4 = (Name:"sam",Age:22);
Console.WriteLine(p4.Name); //sam
//解构赋值
var (n,age) = p4;
Console.WriteLine(n); //sam

元祖的一个比较适用场景就是方法返回多个值,虽然本质上还是一个“值”。

void Main()
{
	var u = FindUser(1);
	var (nn,ss) = FindUser(2);
	Console.WriteLine(u.name+u.score);
	Console.WriteLine(nn+ss);
}

public (string name,int score) FindUser(int id) //返回一个元祖
{
	return ("sam",1000);
}

06、匿名类型(Class)

匿名类型就是无需事先申明,可直接创建任意实例的一种类型。使用 new {}语法创建,创建时申明字段并赋值。

  • 由编译器进行推断创建出一个完整类型。
  • 匿名类型属性都是只读的,同时实现了相等比较、ToString()方法。
var u = new { Name = "same", Age = 10, Birthday = DateTime.Now };
Console.WriteLine(u.Name);
//u.Age=120; //只读不可修改

因此,匿名类型也是一种语法糖,由编译器来生成完整的类型。大多数场景都可以由 ValueTuple 代替,性能更好,也不需要额外的类型了。

image.png


07、其他内置类型

7.1、Console

Console 静态类,控制台输入、输出。

成员说明
BackgroundColor获取、设置控制台背景色
ForegroundColor获取、设置控制台前景色
WriteLine(String)输出内容到控制台
ReadLine()接受控制台输入
Beep()播放一个提示音,参数还可以设置播放时长
Clear()清空控制台

7.2、Environment

Environment 静态类,提供全局环境的一些参数和方法,算是比较常用了。

成员说明
CurrentDirectory当前程序的工作目录,是运行态可变的,不一定是exe目录
ProcessPath当前程序exe的地址,.NET 5支持
CurrentManagedThreadId当前托管现线程的ID
Is64BitOperatingSystem获取操作系统是否64位,Is64BitProcess 获取当前进程是否64位进程。
NewLine换行符(\\r\\n
OSVersion获取操作系统信息
ProcessId获取当前进程ID
ProcessorCount获取CPU处理器核心数
UserName获取当前操作系统的用户名
WorkingSet获取当前进程的物理内存量
Exit(Int32)退出进程
GetFolderPath(SpecialFolder)获取系统特定文件夹目录,如临时目录、桌面等
SetEnvironmentVariable设置环境变量

7.2、AppDomain、AppContext

  • AppDomain 是.Net Framework时代的产物,用来表示一个应用程序域,进程中可以创建多个引用程序域,拥有独立的程序集、隔离环境。在.Net Core 中 其功能大大削弱了,不再支持创建AppDomain,就只有一个CurrentDomain了。
  • AppContext 表示全局应用上下文对象,是一个静态类。.NET Core引入的新类,可用来存放一些全局的数据、开关,API比较少。

image.png

AppDomain成员说明
CurrentDomain静态属性,获取当前应AppDomain
BaseDirectory ⭐获取程序跟目录
Load(AssemblyName)加载程序集Assembly
UnhandledException ⭐全局未处理异常 事件,可用来捕获处理全局异常
AppContext成员说明
BaseDirectory获取程序跟目录⭐
TargetFrameworkName获取当前.Net框架版本
GetData(String)获取指定名称的对象数据,SetData 设置数据。
TryGetSwitch(String, Boolean)获取指定名称的bool值数据,SetSwitch 设置数据。

参考资料

  • .NET类型系统①基础
  • C# 文档
  • 日期、时间和时区
  • 《C#8.0 In a Nutshell》

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

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

相关文章

SpringCloud Alibaba Sentinel 流量控制之流控模式实践总结

官网文档&#xff1a;https://sentinelguard.io/zh-cn/docs/flow-control.html wiki地址&#xff1a;https://github.com/alibaba/Sentinel/wiki/%E6%B5%81%E9%87%8F%E6%8E%A7%E5%88%B6 本文版本&#xff1a;spring-cloud-starter-alibaba&#xff1a;2.2.0.RELEASE 如下图所…

【归并排序】| 详解归并排序 力扣912

&#x1f397;️ 主页&#xff1a;小夜时雨 &#x1f397;️专栏&#xff1a;归并排序 &#x1f397;️如何活着&#xff0c;是我找寻的方向 目录 1. 题目解析2. 代码 1. 题目解析 题目链接: https://leetcode.cn/problems/sort-an-array/ 我们上道题讲过归并排序的核心代码&a…

idea 创建properties文件,解决乱码

设置properties文件编码 点击file->Settings File Encodings->设置utf-8 重新创建.properties文件才生效

MySQL的自增 ID 用完了,怎么办?

MySQL 自增 ID 一般用的数据类型是 INT 或 BIGINT&#xff0c;正常情况下这两种类型可以满足大多数应用的需求。 当然也有不正常的情况&#xff0c;当达到其最大值时&#xff0c;尝试插入新的记录会导致错误&#xff0c;错误信息类似于&#xff1a; ERROR 167 (22003): Out o…

算法期末整理(正在更新中)

一 算法概述 算法的概念 通俗地讲&#xff0c;算法是指解决问题的一种方法或一个过程。更严格地讲&#xff0c;算法是由若干条指令组成的有穷序列。 算法的性质 1.输入&#xff1a;有0个或多个由外部提供的量作为算法的输入。 2.输出&#xff1a;算法产生至少一个量作为输出。…

【机器学习300问】126、词嵌入(Word Embedding)是什么意思?

人类的文字&#xff0c;作为一种高度抽象化的符号系统&#xff0c;承载着丰富而复杂的信息。为了让电脑也能像人类一样理解并处理这些文字&#xff0c;科学家们不断探索各种方法&#xff0c;以期将人类的语言转化为计算机能够理解的格式。 一、One-Hot编码的不足 在自然语言处…

每月策略会议

周一顾问策略会议&#xff0c;对于企业辅导而言&#xff0c;领导力是可以培训的&#xff0c;而决策力不是靠培训就能达成&#xff0c;是需要反复训练和反思。从最为关心的一个状况出发&#xff0c;去行动才会有结果&#xff0c;有了结果反思我们的假设是否有盲区是否有误才有可…

LVGL开发教程-Grid(网格布局)

系列文章目录 知不足而奋进 望远山而前行 目录 系列文章目录 文章目录 前言 1. 常用方法 2. 代码实现 总结 前言 网格布局&#xff08;Grid Layout&#xff09;是一种强大的布局方式&#xff0c;它允许将项目按照行和列的二维表格方式进行排列。LVGL&#xff08;Little…

分布式之日志系统平台ELK

ELK解决了什么问题 我们开发完成后发布到线上的项目出现问题时(中小型公司),我们可能需要获取服务器中的日志文件进行定位分析问题。但在规模较大或者更加复杂的分布式场景下就显得力不从心。因此急需通过集中化的日志管理,将所有服务器上的日志进行收集汇总。所以ELK应运而生…

Android Glide, first start based on loadThumbnail, Kotlin(二)

Android Glide, first start based on loadThumbnail, Kotlin&#xff08;二&#xff09; Android Glide, first start based on loadThumbnail, Kotlin&#xff08;一&#xff09;中有个小问题&#xff0c;通过loadThumbnail()采集到的缩略图真的就是整张图片的完整缩略图&…

NET Core C# 中的Action委托:语法、用法和示例_2024-06-19

Action委托是一个内置的泛型委托类型。此委托使您的程序更具可读性和效率&#xff0c;因为您无需定义自定义委托&#xff0c;如以下示例所示。 它在 System 命名空间下定义。它没有输出参数&#xff0c;输入参数最少为 1 个&#xff0c;最多为 16 个。 Action委托通常用于具有…

高压电阻器支持牙科 X 射线成像的准确性

为了捕获患者牙齿和颌骨的足够图像&#xff0c;牙医依靠锥形束计算机断层扫描 &#xff08;CBCT&#xff09; 系统的先进 3D 成像。CBCT系统的输出对于准确诊断口腔健康问题和随后的治疗计划至关重要。为了确保这些图像的可靠性&#xff0c;CBCT系统制造商利用了Exxelia Ohmcra…

【bug】配置SpringCloudAlibaba AI的maven依赖问题

问题描述 尝鲜alibaba的ai模块&#xff0c;maven依赖一直报找不到包&#xff0c;报错如下 Unresolved dependency: org.springframework.ai:spring-ai-core:jar:0.8.1原因分析&#xff1a; 由于是按照官方文档配置的&#xff0c;所以检查了很多遍maven配置&#xff0c;加上去…

给电脑bios主板设置密码

增强安全性&#xff1a;防止未经授权的人员更改 BIOS 中的重要设置&#xff0c;如启动顺序、硬件配置等。这有助于保护计算机系统的稳定性和数据的安全性。防止恶意篡改&#xff1a;阻止可能的攻击者或恶意软件通过修改 BIOS 设置来破坏系统或获取敏感信息。数据保护&#xff1…

阿里云 debian10.3 sudo apt-get updat 报错的解决方案

阿里云全新的debian10.3(buster)镜像&#xff0c;却无法正常执行 sudo apt-get update。主要报错信息如下&#xff1a; Err:6 http://mirrors.cloud.aliyuncs.com/debian buster-backports Release404 Not Found [IP: 100.100.2.148 80] Err:3 http://mirrors.cloud.aliyuncs…

【JavaEE 进阶(五)】SpringBoot日志

❣博主主页: 33的博客❣ ▶️文章专栏分类:JavaEE◀️ &#x1f69a;我的代码仓库: 33的代码仓库&#x1f69a; &#x1faf5;&#x1faf5;&#x1faf5;关注我带你了解更多进阶知识 目录 1.前言2.日志使用2.1打印日志2.2 门面模式(外观模式)2.3SLF4J框架2.4日志格式说明 3.Sl…

MySQL----配置主从复制

环境 master(CtenOS7)&#xff1a;192.168.200.131 ----ifconfig查看->ens33->inet slave(win10)&#xff1a;192.168.250.52 ----ipconfig查看->无线局域网适配器 WLAN:-> IPv4 地址 保证两个环境中MySQL版本一致 网络互通 win&#xff1a;ping 192.168.200.13…

NL2SQL进阶系列(1):DB-GPT-Hub、SQLcoder、Text2SQL开源应用实践详解

1. MindSQL(库) MindSQL 是一个 Python RAG&#xff08;检索增强生成&#xff09;库&#xff0c;旨在仅使用几行代码来简化用户与其数据库之间的交互。 MindSQL 与 PostgreSQL、MySQL、SQLite 等知名数据库无缝集成&#xff0c;还通过扩展核心类&#xff0c;将其功能扩展到 Sn…

【五子棋】C语言教程

Hi~&#xff01;这里是奋斗的小羊&#xff0c;很荣幸您能阅读我的文章&#xff0c;诚请评论指点&#xff0c;欢迎欢迎 ~~ &#x1f4a5;&#x1f4a5;个人主页&#xff1a;奋斗的小羊 &#x1f4a5;&#x1f4a5;所属专栏&#xff1a;C语言 &#x1f680;本系列文章为个人学习…

webhook-k8s API和apimachinery版本高于Client-go

1. 问题 使用go mod tidy 存在丢弃的版本 go: downloading github.com/josharian/intern v1.0.0 go: finding module for package k8s.io/api/flowcontrol/v1alpha1 go: simple-webhook/types importsk8s.io/client-go/rest tested byk8s.io/client-go/rest.test importsk8s.…