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

TypeScript 基础类型与类型声明

前言

在 JavaScript 中,变量是没有类型的,变量的值的类型是在运行时确定的,这被称为动态类型
这意味着可以在不同的时间将不同类型的值赋给同一个变量,并且 JavaScript 会在运行时根据当前赋给变量的值来确定其类型。
示例:

let a;   // 声明一个变量 a 
a = 10;  // 此时 a 的类型被确定为数字类型
a = "hello JavaScript"; // 现在 a 的类型变为字符串类型

a 的类型随着每次赋值而改变。
JavaScript 会在运行时根据实际赋给变量的值来自动调整和处理其类型。这种动态类型的特性使得 JavaScript 非常灵活,但也可能导致一些难以察觉的错误,因为类型的变化可能会在不经意间发生。

例如,想要一个变量是数字并进行数学运算,但它在运行时被意外地赋值为字符串,就会出错。

let a = 10;
let b = 5;
console.log(a + b); // 15
// 假如经历了一系列逻辑操作,需要重新对 b 赋值 并计算结果
b = "5";
console.log(a + b);  // "105",假如在别的地方要使用这个结果,会导致难以排查的错误。

JavaScript是动态类型语言,对类型的检查和约束相对较弱。

TypeScript 是 JavaScript 的超集,它支持与JavaScript几乎相同的数据类型,在 JavaScript 的基础上增加了静态类型系统。这意味着在 TypeScript 中,开发者需要在编写代码时,可以选择添加类型注释来明确指定变量、函数参数、函数返回值等的类型。

注意:TypeScript 的类型注释将始终位于被输入的内容之后。

基础类型

string:字符串类型。

// 声明一个变量 str,同时指定 str 的类型为 string
let str: string;
// str 的类型设置为 string,从此以后,str 的值只能是 字符串类型
str = "Hello"; // 字符串类型
str = 123; // 编译错误: Type 'number' is not assignable to type 'string'.

在编写代码时,编辑器报错:不能将类型“number”分配给类型“string”。
因为变量str的类型是string

可以使用模版字符串

let name: string = `张三`;
let desc: string = `我的名字是 ${name}`;

number:数字类型。

数字类型不分intfloat,全是number

let decLiteral: number = 6;
let hexLiteral: number = 0xf00d;
let binaryLiteral: number = 0b1010;
let octalLiteral: number = 0o744;

除了支持十进制和十六进制字面量,TypeScript还支持ECMAScript 2015中引入的二进制和八进制字面量。

boolean:布尔类型。

布尔类型只有两个值true/ false

let isDone: boolean = false;

始终使用stringnumberboolean来表示类型。

数组类型

TypeScript有两种方式可以定义数组。

  1. 在基础数据类型后面接上 [],表示由此类型元素组成的一个数组:
let list1: number[] = [1, 2, 3];  // 数字数组,数组的每个元素都是number类型
let list2: string[] = ["list1", "list2"]; // 字符串数组,数组的每个元素都是string类型
let list3: boolean[] = [true, false, true]; // 布尔数组,数组的每个元素都是boolean类型let arr: string[][] = [["a", "b"], ["c", "d"]]; // 声明一个二维字符串数组。
  1. 使用数组泛型,Array<元素类型>
let list1: Array<number> = [1, 2, 3];
let list2: Array<string> = ["list1", "list2"];
let list3: Array<boolean> = [true, false, true];

元组 Tuple

TypeScript 中的元组(Tuple)是一种特殊的数组类型。
元组类型允许表示一个已知元素数量和类型的数组,各元素的类型不必相同。

特点:

  1. 固定的元素数量和类型顺序
    • 元组中的元素数量是明确的,并且每个位置的元素类型是固定的。
  2. 混合类型
    • 可以在一个元组中包含不同类型的元素。

示例:

// 定义一个包含字符串、数字和布尔值的元组
let myTuple: [string, number] = ['Hello', 42];
// 语句没有报错,why?
myTuple.push("为什么这句不报错?"); 
// 访问元组中的元素,通过索引
console.log(myTuple[0]);  // 'Hello'
console.log(myTuple[1]);  // 42
// 错误:Type 'string' is not assignable to type 'number'.(不能将类型“string”分配给类型“number”。)
myTuple[1] = 'not a number';  // 编译错误:Type 'string' is not assignable to type 'number'.// 错误:Type 'true' is not assignable to type 'undefined'.(不能将类型“true”分配给类型“undefined”。)
// 错误:Tuple type '[string, number]' of length '2' has no element at index '2'.(长度为 "2" 的元组类型 "[string, number]" 在索引 "2" 处没有元素。)
myTuple[2] = true; // 错误:Argument of type 'boolean' is not assignable to parameter of type 'string | number'.(类型“boolean”的参数不能赋给类型“string | number”的参数。)
myTuple.push(true);// 语句没有报错,why?
// myTuple.push("world"); 

TypeScript 的元组和数组的区别:

  • 元组:具有固定数量的元素,且每个元素的类型是明确且固定的。元组对每个位置的元素类型有严格的约束。
  • 数组:元素数量可以动态变化。如果指定了类型,如 number[] ,则要求所有元素都是指定的类型;如果未指定类型,元素类型可以不同(any类型)。

枚举

枚举(Enum)类型是对Java Script标准数据类型的一个补充。
枚举(Enum)是一种为一组数值赋予有意义名称的方式。
默认情况下,从 0 开始为元素编号。

enum Color {Red, Green, Blue}
console.log(Color);
// 输出以下结果
// {
//   "0": "Red",
//   "1": "Green",
//   "2": "Blue",
//   "Red": 0,
//   "Green": 1,
//   "Blue": 2
// } 

代码定义了一个名为 Color 的枚举类型,其中 Red 被初始化为 0Green1Blue2
也可以手动为枚举成员赋值:

enum Color1 {Red = 11,Green = 22,Blue = 33
}
console.log(Color1);
// 输出
// {
//   "11": "Red",
//   "22": "Green",
//   "33": "Blue",
//   "Red": 11,
//   "Green": 22,
//   "Blue": 33
// } 

枚举成员可以通过两种方式访问:

let c: Color = Color.Red;  // 通过枚举名.成员名
console.log(c);  // 输出 0(默认情况)let colorName = Color[2];  // 通过枚举值获取枚举名
console.log(colorName);  // 输出 "Green"(默认情况)

Any

当一个变量被声明为 any 类型时,它可以被赋予任何类型的值,并且在对其进行操作时,TypeScript 编译器不会进行类型检查。
any 完全放弃了类型检查。

// 显式声明变量为any类型
let variable: any = 5;
variable = "Hello"; 
variable = true; let list: any[] = [1, true, "free"];  // list 包含了不同的类型的数据
list[1] = 66;// 隐式声明变量为any类型
// 声明变量 并且 不指定类型, TS 解析器会自动判断变量的类型为any
let variable1;
variable1 = "Hello"; 
variable1 = true; 

在上述代码中,variablevariable1 可以被随意赋值为不同类型的值。

any 类型的变量还可以赋值给任意类型的变量:

let variable: any = 5;
variable = "Hello"; 
variable = true; let str : string;
str = variable;
console.log(str);  // true; TS类型检查器不会再检查 变量 str 。

通常,只有在确实无法确定变量类型或者需要与旧的 JavaScript 代码进行交互且类型难以明确时,才建议使用 any 类型。

unknown

unknown 类型表示一个值的类型是未知的。
只有 any 类型和 unknown 类型的值可以赋给 unknown 类型的变量。
unknown 类型是一种比 any 更安全的类型,对 unknown 类型的值进行操作是受到限制的。
例如,如果有一个变量 x 的类型是 unknown ,在对其进行操作之前,必须先进行类型断言或类型缩小的检查:

let x: unknown;
// 错误,不能直接对 unknown 类型的值进行操作
// x.toUpperCase(); // 报错:x 的类型是 “未知”
if (typeof x ==='string') {// 经过类型缩小检查后,可以进行操作x.toUpperCase();
}

可以对 x 进行任意赋值:

let variable: any;
let x: unknown;
x = "Hello";  // 合法,因为可以将 any 或 unknown 类型的值赋给 unknown 类型的变量
x = true;    
x = variable; // 合法,因为可以将 any 或 unknown 类型的值赋给 unknown 类型的变量

不能将 unknown 类型的变量 赋值给 除any类型外的 其他类型的变量:

let str : string;
str = x; // 不能将类型“unknown”分配给类型“string”。let variable: any;
variable = x; // 合法,因为 any 类型可以被赋值任意类型的值

unknown 类型的主要用途是在处理可能来自不可信或动态来源的数据时,提供一种更严格的类型控制,以防止意外的类型错误。

unknown 和 any 的区别

  1. 类型安全性:
    • any 完全放弃了类型检查,可以对 any 类型的变量执行任何操作,而 TypeScript 编译器不会产生错误。
    • unknown 则更安全,对 unknown 类型的变量进行操作时,TypeScript 编译器会要求先进行类型断言或类型缩小检查,以确保操作的合法性。
  2. 可赋值性:
    • 任何类型的值都可以赋给 any 类型的变量。
      any 类型的变量可以被赋值给任意类型的变量,并关闭该变量的TypeScript 静态类型检查。
    • 只有 any 类型和 unknown 类型的值可以赋给 unknown 类型的变量。
      unknown 类型的变量不可以被赋值给 除 any 类型外 的 其他类型的变量。
  3. 操作限制:
    • 对于 any 类型的变量,可以直接调用任何方法和访问任何属性,而无需考虑其实际类型。
    • 对于 unknown 类型的变量,在没有进行类型断言或缩小检查之前,不能直接调用方法或访问属性。

Void

在 TypeScript 中,void 类型用于表示没有任何返回值的函数。
当变量被声明为 void 类型时,只能被赋值为 undefined :

let unusable: void = undefined;
let unusable1: void = null; // 报错:不能将类型“null”分配给类型“void”。

void 类型用来表示函数没有返回值的情况。当你尝试将 null 赋值给一个 void 类型的变量时,编译器会报错,因为 null 表示对象的引用,而 void 不是一个对象,它只是一个表示无返回值的特殊类型。
在这里插入图片描述
当一个函数没有返回值时,你通常会见到其返回值类型是 void

function printMsg(): void {console.log("This is my message");
}function noReturn(): void {return // return undefined
}

Null 和 Undefined

在 TypeScript 中,null的类型是nullundefined 的类型是undefined

默认情况下nullundefined是所有类型的子类型。 就是说你可以把 nullundefined赋值给其他类型的变量。

let u: undefined = undefined; // 变量类型是undefined,值是undefined
let n: null = null;  // 变量类型是null ,值是null let num: number = null;  // 合法,但不推荐
let str: string;
console.log(str);  // 输出 undefined

在 TypeScript 的严格空值检查模式(通过在 tsconfig.json 中设置 "strictNullChecks": true )下,对 nullundefined 的处理更加严格。例如,函数参数不能默认是 nullundefined ,除非明确指定类型为 number | nullstring | undefined 这样的联合类型。

文中所有例子都假设"strictNullChecks": false

Never

never类型表示的是那些永不存在的值的类型。

在 TypeScript 中,一般不会直接创建 never 类型的变量。因为 never 表示永远不会有值的类型。
但在某些复杂的类型推导或函数的返回类型中,可能会出现被推断为 never 类型的情况。

它通常用于以下几种情况:

  1. 函数中抛出异常或进入一个无限循环:
// 返回never的函数必须存在无法达到的终点
function error(message: string): never {throw new Error(message);
}
// 返回never的函数必须存在无法达到的终点
function infiniteLoop(): never {while (true) {}
}// 推断的返回值类型为never
function fail() {return Error("Something failed");
}
  1. 用来表示一个函数的返回值类型,当这个函数永远不会正常返回(即总是以抛出异常结束)。

例如,如果一个函数用于处理所有可能的情况,并且对于某些输入它应该抛出错误,那么其返回类型可以是 never

function exhaustiveCheck(x: string): never {if (x === 'a') {// 一些处理逻辑} else if (x === 'b') {// 一些处理逻辑} else {throw new Error('Unexpected value');}
}

object

在 TypeScript 中,object 类型用于表示非原始类型,除 numberstringbooleansymbolnullundefined 外的类型。

let obj: Object;
obj = { name: 'John' };  // obj 是一个对象
obj = function() {};  // obj是一个函数,函数也是对象let arr: Object = [1, 2, 3];  // 数组是特殊的对象

在JavaScript中,几乎所有的数据类型都可以被视为对象,或者具有对象的某些特性。

基本数据类型如数字、字符串、布尔值,在 JavaScript 中都有对应的对象形式。像数字 5 对应的对象形式是 new Number(5) ,字符串 "hello" 对应的对象形式是 new String("hello") ,布尔值 true 对应的对象形式是 new Boolean(true)
函数也是对象,它们可以具有属性和方法。
数组也是一种特殊的对象。
甚至一些内置的全局对象,如 Math 、 Date 等,也提供了各种功能和方法。
示例:

function myFunction() {console.log('Hello!');
}
myFunction.property = 'Some value';  // 函数可以添加属性let num = 5;
let numObj = new Number(num);  // 将数字转换为对象形式

在 TypeScript 中,直接声明一个变量的类型为 object 相对较少使用,并且通常不是最佳实践。
只是声明变量的类型为 object ,它并不能明确对象应该具有哪些具体的属性,可能会导致类型检查不够严格和代码的可读性降低。
object 类型通常不是用于简单地判断一个变量是不是一个普通的对象,而是更侧重于描述对象所具有的特定属性结构。
(大多数情况下,object 被用来限制对象中的属性,而不是限制变量的类型是不是一个对象。)

// 声明一个对象类型的变量 obj ,并且指定其属性 name 的类型为字符串
let obj: {name: string};  
obj = {}; // Error: Property 'name' is missing in type '{}' but required in type '{ name: string; }'.
// (类型 "{}" 中缺少属性 "name",但类型 "{ name: string; }" 中需要该属性。)// 对象obj的赋值必须和obj声明的结构一模一样
obj = {name: "张三"};
obj = {name: "张三", age: 18};  // Error: Object literal may only specify known properties, and 'age' does not exist in type '{ name: string; }'.
// (对象字面量只能指定已知属性,并且“age”不在类型“{ name: string; }”中。)

属性名后面加上?,表示是可选属性:

// 这里的 ? 表示 age 属性是可选的
let obj: { name: string, age?: number };
obj = {name: "张三"};  // 合法, 因为 age 是可选属性
obj = {name: "张三", age: 18}; // 合法

假设对象obj必须要有name属性,其余属性可有可无:

let obj: { name: string, [propName: string]:any };
obj = {name: "张三", age: 18}; // 合法
obj = {name: "张三", age: 18, sex: "male"}; // 合法// Error: Property 'name' is missing in type '{ age: number; }' but required in type '{ [propName: string]: any; name: string; }'.
obj = {age: 18}; // 不合法,因为没有 'name' 属性// Error: Type 'number' is not assignable to type 'string'.
obj = {name: 18}; // 因为 'name' 属性不是字符串类型
  1. let obj 声明了一个变量 obj
  2. { name: string, [propName: string]:any } 定义了这个变量的类型。
    • name: string 明确指定了 obj 必须具有一个名为 name 的属性,且这个属性的值必须是字符串类型。
    • [propName: string]:any 这部分是一个索引签名。propName 是一个变量名,在这里只是表示任意属性的名称。string 表示属性名的类型是字符串。any 表示对应属性的值可以是任何类型。
      这意味着除了必须存在的 name 属性是字符串类型外,obj 还可以有任意数量的其他属性,这些属性的名称是字符串,并且值可以是任何类型。

使用object类型,可以更好的表示像Object.create这样的API。

declare function create(o: object | null): void;

declare 关键字用于声明存在一个在其他地方定义(可能是在外部模块、全局环境或其他源文件)的函数。
这段代码声明了一个名为 create 的函数,它接受一个参数 oo 的类型可以是一个对象或者 null ,并且这个函数没有返回值(void)。
调用create 函数:

create({ key: 'value' }); 
create(null); create(5);  // 错误,因为 5 不是对象也不是 null
create('string');  // 错误,因为 'string' 不是对象也不是 null

联合类型声明

  1. 基本用法
let value: string | number; // 表示 value 可以是字符串或者数字。
value = "hello typescript"; // 合法
value = 123; // 合法
value = [];  // 不合法
  1. 函数参数
function printValue(value: string | number) {if (typeof value ==='string') {console.log(`It's a string: ${value}`);} else {console.log(`It's a number: ${value}`);}
}printValue("World");  // 合法
printValue(456);  // 合法
  1. 与对象类型相结合
interface Person {name: string;age: number;
}interface Animal {species: string;
}let entity: Person | Animal;entity = { name: "John", age: 30 };  // 合法
entity = { species: "Dog" };        // 合法
entity = { name: "John", age: 30, species: "Dog" };  // 合法

声明了一个变量 entity ,其类型为 PersonAnimal 的联合类型,这意味着 entity 可以被赋值为符合 Person 接口结构的对象,或者符合 Animal 接口结构的对象,也可以同时符合 PersonAnimal 结构的对象。
通过联合类型的声明,使得 entity 变量能够灵活地接受不同类型但具有特定结构的对象值。

  1. 数组中的联合声明
let arr: (string | number)[];
arr = ["Hello", 123, "World", 456]; // 合法arr = ["Hello", 123, "World", true]; // 不合法
// Error: Type 'boolean' is not assignable to type 'string | number'.

(string | number)[] 是数组的类型声明。其中 string | number 是联合类型,表示数组中的元素可以是字符串类型(string)或者数字类型(number)。

联合类型为处理可能具有多种类型的值提供了灵活性。

交叉类型声明

在 TypeScript 中,交叉类型(Intersection Type)用于将多个类型合并为一个新的类型,该新类型具有所合并类型的所有成员。
交叉类型使用 & 符号来创建。
例如,如果有两个接口 UserEmployee

interface User {name: string;age: number;sayYes(): void;
}interface Employee {jobTitle: string;salary: number;sayNo(): void;
}

创建一个交叉类型 UserEmployee

type UserEmployee = User & Employee;// 错误: “UserEmployee”仅表示类型,但在此处却作为值使用。
console.log(UserEmployee ); // Error: 'UserEmployee' only refers to a type, but is being used as a value here.

UserEmployee 类型的对象同时具有 UserEmployee 接口中定义的所有属性和方法:

let person: UserEmployee = {name: "张三",age: 30,jobTitle: "Developer",salary: 10000,sayYes() {console.log('sayYes!');},sayNo() {console.log('sayNo!');}
};

在交叉类型中,需要注意以下几点:

  1. 同名属性的类型必须兼容。如果两个接口中都有一个名为 id 的属性,但一个是字符串类型,另一个是数字类型,就会导致类型错误。
  2. 方法也会被合并,如果两个接口中有同名的方法,那么它们的实现需要保持一致,否则也会导致类型错误。
  3. 交叉类型可以用于多个接口、类型别名甚至具体的对象类型的合并。

交叉类型在一些场景中非常有用,比如需要一个对象同时满足多个不同的类型约束,或者需要将多个相关但又有所不同的类型组合在一起。

相关文章:

TypeScript 基础类型与类型声明

前言 在 JavaScript 中&#xff0c;变量是没有类型的&#xff0c;变量的值的类型是在运行时确定的&#xff0c;这被称为动态类型。 这意味着可以在不同的时间将不同类型的值赋给同一个变量&#xff0c;并且 JavaScript 会在运行时根据当前赋给变量的值来确定其类型。 示例&…...

算法:BFS 解决多源最短路问题

目录 多源最短路 题目一&#xff1a;矩阵 题目二&#xff1a;飞地的数量 题目三&#xff1a;地图中的最高点 题目四&#xff1a;地图分析 多源最短路 首先想要知道多源最短路&#xff0c;就先要明白单源最短路&#xff0c;bfs解决单源最短路问题前面学习过&#xff0c;单…...

grep工具的使用

grep [options]…… pattern [file]…… 工作方式&#xff1a; grep 在一个或者多个文件中搜索字符串模板&#xff0c;如果模板中包括空格&#xff0c;需要使用引号引起来&#xff0c;模 板后的所有字符串会被看作是文件名。 工作结果&#xff1a;如果模板搜索成功&#xf…...

Langchain核心模块与实战[9]:RAG检索增强生成[文本向量化、实战ChatDoc智能文档助手]

Langchain核心模块与实战[9]:RAG检索增强生成[文本向量化、实战ChatDoc智能文档助手] 参考文章可以使用国产LLM进行下述项目复现: 初识langchain[1]:Langchain实战教学,利用qwen2.1与GLM-4大模型构建智能解决方案[含Agent、tavily面向AI搜索]langchain[2]:Langchain实战教…...

Java从入门到精通(十五) ~ IO流

晚上好&#xff0c;愿这深深的夜色给你带来安宁&#xff0c;让温馨的夜晚抚平你一天的疲惫&#xff0c;美好的梦想在这个寂静的夜晚悄悄成长。 目录 前言 什么是IO流&#xff1f; IO流的作用&#xff1a; 一、基础流 1. 字节流 1.1 字节输入流 FileInputStream 1.2 字节…...

C Primer Plus 第4章——第二篇

你该逆袭了 第4章&#xff1a;重点摘录 五、scanf( )1、使用 scanf( )(1)转换说明 *(2)转换说明 数字(3)转换说明 hh(4)scanf 中其他的转换说明&#xff0c;不作详细解释&#xff0c;用到的时候再去学习即可 2、从 scanf( ) 角度 看 输入3、格式字符串中的普通字符4、scanf&…...

优化海外用户体验,畅通支付路径!来了解WeTest的本地化支付测试方案

在APP出海的全生命周期中&#xff0c;支付系统的稳定运行是至关重要的一环。随着产品服务覆盖地区的拓展、APP内付费功能的拓展以及不同地区用户对多样化支付渠道的需求增加&#xff0c;出海APP的当地支付体验的优劣直接影响到海外用户的消费决策。 然而海外支付风控升级&#…...

VUE框架面试整理-模板语法

Vue.js 的模板语法允许你声明式地将数据绑定到 DOM。以下是一些常见的模板语法和用法: 插值 插值语法用于在 HTML 中插入数据。 <p>{{ message }}</p>data:...

【C语言】fseek、ftell以及rewind函数(随机文件读写)

文章目录 前言1. fseek1.1 fseek函数原型1.2 fseek函数的形式参数1.3 fseek实例演示 2. ftell2.1 ftell函数原型2.2 ftell函数的实例演示 3. rewind3.1 rewind函数原型3.2 rewind函数实例演示 前言 在之前&#xff0c;我讲过文件的顺序读写。但是我们可不可以随机读写文件呢&a…...

使用 Elastic Observability 中的 OpenTelemetry 进行基础设施监控

作者&#xff1a;来自 Elastic ISHLEEN KAUR 将 OpenTelemetry 与 Elastic Observability 相结合&#xff0c;形成应用程序和基础设施监控解决方案。 在 Elastic&#xff0c;我们最近决定全面采用 OpenTelemetry 作为首要的数据收集框架。作为一名可观察性工程师&#xff0c;我…...

征服数据结构中的时间和空间复杂度

目录 时间复杂度推导大O方法求解时间复杂度的方法普通顺序结构单循环双循环递归Master定理&#xff08;主定理&#xff09;递归树方法 空间复杂度 一个算法的好坏根据什么来判断呢&#xff1f;有两种一种是时间效率&#xff0c;一种是空间效率。时间效率也可称为时间复杂度&…...

springboot Security vue

在使用Spring Boot Security与Vue.js构建前后端分离的应用时&#xff0c;你需要处理几个关键的技术点&#xff0c;包括认证&#xff08;Authentication&#xff09;和授权&#xff08;Authorization&#xff09;&#xff0c;以及如何处理跨域请求&#xff08;CORS&#xff09;、…...

13. 计算机网络HTTPS协议(一)

1. 前言 在上一章节中我们介绍了 HTTP 协议相关的面试题目,作为 HTTP 协议的扩展,HTTPS 协议也经常被面试官提起。 因为对于大部分的前端、后端开发者,都接触不到 HTTPS 协议的开发场景,因为我们往往只关注请求路径后缀,例如关注 URL: /get/username,而非路径全称 htt…...

Bean的作用域和生命周期

Bean的作用域 我们先来看下面这段代码 首先是一个Dog类 &#xff08;此处使用lombok来完成setter、getter、toString方法&#xff09; Setter Getter public class Dog {private String name;} 然后在DogBeanConfig类里面写一个返回Dog的方法&#xff0c;并将这个方法的返…...

【Qt】QMainWindow之菜单栏

目录 一.菜单栏 1.概念 2.组成 二.代码创建菜单栏 1.创建菜单栏 2.在菜单栏中添加菜单 3.在菜单中添加菜单项 三.图形化创建菜单栏 1.在打开Qt自带的ui文件界面后&#xff0c;得到以下界面 2.双击点击界面中&#xff08;在这里输入&#xff09;&#xff0c;在菜单栏中进行…...

uni-app封装组件实现下方滑动弹出模态框

子组件 <template><div class"bottom-modal" :class"{show: showModal}"><div class"modal-content" :class"{show: showModal}"><!-- 内容区域 --><slot></slot></div></div></…...

MATLAB(15)分类模型

一、前言 在MATLAB中&#xff0c;实现不同类型的聚类&#xff08;如K-means聚类、层次聚类、模糊聚类&#xff09;和分类&#xff08;如神经网络分类&#xff09;需要用到不同的函数和工具箱。下面我将为每种方法提供一个基本的示例代码。 二、实现 1. K-means聚类 % 假设X是…...

非虚拟机安装Centos7连接wifi并开机自动联网

一&#xff1a;确认网卡名称 ip addr 无线网卡是以 w 开头&#xff0c;确定是wlp4s0 &#xff0c;有的是 wlp5s0 二&#xff1a;配置网络 wpa_supplicant -B -i wlp4s0 -c <(wpa_passphrase "网络的名字" “网络的密码“) 设置自动分配IP dhclient wlp4s0 三&…...

怎么选择的开放式耳机好用?2024超值耳机分享!

耳机在当前数字化时代已成为我们生活、娱乐乃至工作中的重要部分。随着市场需求的增长&#xff0c;消费者对耳机的期望也在提高&#xff0c;他们不仅追求音质的卓越&#xff0c;还关注佩戴的舒适度和外观设计。虽然传统的入耳式和半入耳式耳机在音质上往往能够满足人们&#xf…...

Web 框架

Web 框架 Web服务器Web服务器的主要功能常见的Web服务器软件包 Web 框架常用 Python Web 框架选择Python Web框架的考虑因素 WSGIWSGI的主要特点WSGI的工作原理常见的WSGI服务器和框架&#xff1a; 静态资源定义与特点静态资源的类型静态资源的管理与优化 动态资源定义与特点动…...

Linux应用开发之网络套接字编程(实例篇)

服务端与客户端单连接 服务端代码 #include <sys/socket.h> #include <sys/types.h> #include <netinet/in.h> #include <stdio.h> #include <stdlib.h> #include <string.h> #include <arpa/inet.h> #include <pthread.h> …...

【力扣数据库知识手册笔记】索引

索引 索引的优缺点 优点1. 通过创建唯一性索引&#xff0c;可以保证数据库表中每一行数据的唯一性。2. 可以加快数据的检索速度&#xff08;创建索引的主要原因&#xff09;。3. 可以加速表和表之间的连接&#xff0c;实现数据的参考完整性。4. 可以在查询过程中&#xff0c;…...

Mybatis逆向工程,动态创建实体类、条件扩展类、Mapper接口、Mapper.xml映射文件

今天呢&#xff0c;博主的学习进度也是步入了Java Mybatis 框架&#xff0c;目前正在逐步杨帆旗航。 那么接下来就给大家出一期有关 Mybatis 逆向工程的教学&#xff0c;希望能对大家有所帮助&#xff0c;也特别欢迎大家指点不足之处&#xff0c;小生很乐意接受正确的建议&…...

【磁盘】每天掌握一个Linux命令 - iostat

目录 【磁盘】每天掌握一个Linux命令 - iostat工具概述安装方式核心功能基础用法进阶操作实战案例面试题场景生产场景 注意事项 【磁盘】每天掌握一个Linux命令 - iostat 工具概述 iostat&#xff08;I/O Statistics&#xff09;是Linux系统下用于监视系统输入输出设备和CPU使…...

令牌桶 滑动窗口->限流 分布式信号量->限并发的原理 lua脚本分析介绍

文章目录 前言限流限制并发的实际理解限流令牌桶代码实现结果分析令牌桶lua的模拟实现原理总结&#xff1a; 滑动窗口代码实现结果分析lua脚本原理解析 限并发分布式信号量代码实现结果分析lua脚本实现原理 双注解去实现限流 并发结果分析&#xff1a; 实际业务去理解体会统一注…...

什么是Ansible Jinja2

理解 Ansible Jinja2 模板 Ansible 是一款功能强大的开源自动化工具&#xff0c;可让您无缝地管理和配置系统。Ansible 的一大亮点是它使用 Jinja2 模板&#xff0c;允许您根据变量数据动态生成文件、配置设置和脚本。本文将向您介绍 Ansible 中的 Jinja2 模板&#xff0c;并通…...

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…...

OPENCV形态学基础之二腐蚀

一.腐蚀的原理 (图1) 数学表达式&#xff1a;dst(x,y) erode(src(x,y)) min(x,y)src(xx,yy) 腐蚀也是图像形态学的基本功能之一&#xff0c;腐蚀跟膨胀属于反向操作&#xff0c;膨胀是把图像图像变大&#xff0c;而腐蚀就是把图像变小。腐蚀后的图像变小变暗淡。 腐蚀…...

2023赣州旅游投资集团

单选题 1.“不登高山&#xff0c;不知天之高也&#xff1b;不临深溪&#xff0c;不知地之厚也。”这句话说明_____。 A、人的意识具有创造性 B、人的认识是独立于实践之外的 C、实践在认识过程中具有决定作用 D、人的一切知识都是从直接经验中获得的 参考答案: C 本题解…...

Ubuntu Cursor升级成v1.0

0. 当前版本低 使用当前 Cursor v0.50时 GitHub Copilot Chat 打不开&#xff0c;快捷键也不好用&#xff0c;当看到 Cursor 升级后&#xff0c;还是蛮高兴的 1. 下载 Cursor 下载地址&#xff1a;https://www.cursor.com/cn/downloads 点击下载 Linux (x64) &#xff0c;…...