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

wifi管理网站在线设计房屋布局软件

wifi管理网站,在线设计房屋布局软件,cnn头条新闻,网站建设企业蛋糕TypeScript 泛型与类型操作详解#xff08;一#xff09; TypeScript 提供了强大的类型系统#xff0c;其中泛型#xff08;Generics#xff09;和类型操作#xff08;Type Manipulation#xff09;是其核心特性之一。本文将详细介绍 TypeScript 中的泛型及其相关概念一 TypeScript 提供了强大的类型系统其中泛型Generics和类型操作Type Manipulation是其核心特性之一。本文将详细介绍 TypeScript 中的泛型及其相关概念并通过案例代码进行说明。 一、泛型简介 泛型允许在定义函数、接口或类时不预先指定具体的类型而是在使用时指定类型。这种方式提高了代码的复用性和灵活性。 为什么使用泛型 提高代码重用性提供更好的类型安全性减少使用 any 类型的需要在编译时捕获类型错误 1.1 形式类型参数与实际类型参数 形式类型参数Type Parameters在泛型定义中声明的类型占位符通常使用 T、T, U 等形式。实际类型参数Type Arguments在使用泛型时传入的具体类型。 示例 // 定义一个泛型函数形式类型参数为 T function identityT(arg: T): T {return arg; }// 使用泛型函数实际类型参数为 number let output identitynumber(42); // output 的类型为 number// 也可以让 TypeScript 推断类型 let output2 identity(Hello, TypeScript!); // output2 的类型为 string1.2 泛型约束 有时需要对泛型参数进行约束限制其必须符合某些条件。可以使用 extends 关键字实现。 示例 // 定义一个接口描述必须具有 length 属性的类型 interface Lengthwise {length: number; }// 使用泛型约束限制 T 必须符合 Lengthwise 接口 function loggingIdentityT extends Lengthwise(arg: T): T {console.log(arg.length); // 现在可以安全地使用 length 属性return arg; }// 正确使用 loggingIdentity(Hello); // string 符合 Lengthwise 接口// 错误使用会在编译时报错 // loggingIdentity(42); // number 不符合 Lengthwise 接口二、泛型函数 泛型函数允许函数在调用时指定类型参数从而实现更灵活的参数和返回值类型。 示例 // 泛型函数返回第一个元素 function getFirstElementT(arr: T[]): T {return arr[0]; }let firstNumber getFirstElementnumber([1, 2, 3]); // firstNumber 的类型为 number let firstString getFirstElementstring([a, b, c]); // firstString 的类型为 string三、泛型接口 接口也可以是泛型的用于定义泛型函数的类型或泛型对象的结构。 示例 // 定义一个泛型接口描述一个包含键值对的对象 interface PairK, V {key: K;value: V; }// 使用泛型接口 let user: Pairstring, number {key: age,value: 30 };四、泛型类型别名 类型别名可以使用泛型来创建可复用的复杂类型。 示例 // 定义一个泛型类型别名描述一个数组或对象 type ContainerT T[] | { value: T };// 使用泛型类型别名 let numberContainer: Containernumber [1, 2, 3]; let stringContainer: Containerstring { value: Hello };五、泛型类 类也可以是泛型的用于创建可复用的组件。 示例 // 定义一个泛型类表示一个栈 class StackT {private elements: T[] [];push(element: T) {this.elements.push(element);}pop(): T | undefined {return this.elements.pop();}peek(): T | undefined {return this.elements[this.elements.length - 1];} }// 使用泛型类 let numberStack new Stacknumber(); numberStack.push(1); numberStack.push(2); console.log(numberStack.peek()); // 输出: 2let stringStack new Stackstring(); stringStack.push(a); stringStack.push(b); console.log(stringStack.peek()); // 输出: b六、局部类型 局部类型是指在函数或块作用域内定义的类型。 示例 function processT(value: T) {// 定义一个局部类型type Wrapped { wrapped: T };let wrappedValue: Wrapped { wrapped: value };console.log(wrappedValue); }process(Hello); // 输出: { wrapped: Hello }七、联合类型 联合类型表示一个值可以是几种类型之一使用 | 分隔。 示例 function printId(id: number | string) {console.log(ID:, id); }printId(101); // 输出: ID: 101 printId(202); // 输出: ID: 2027.1 联合类型字面量 联合类型字面量是指字面量值的联合。 示例 type Direction left | right | up | down;function move(direction: Direction) {console.log(Moving, direction); }move(left); // 输出: Moving left // move(forward); // 编译错误7.2 联合类型的类型成员 联合类型的每个成员类型必须符合所有成员类型的共有属性。 示例 interface Bird {fly(): void;layEggs(): void; }interface Fish {swim(): void;layEggs(): void; }function getSmallPet(): Bird | Fish {// ... }let pet getSmallPet(); pet.layEggs(); // 正确 // pet.fly(); // 错误: Fish 类型没有 fly 方法八、交叉类型 交叉类型表示一个值同时符合几种类型使用 分隔。 示例 interface Person {name: string; }interface Employee {employeeId: number; }type PersonEmployee Person Employee;let personEmployee: PersonEmployee {name: Alice,employeeId: 123 };8.1 交叉类型字面量 交叉类型字面量是指字面量值的交叉。 示例 type Color red blue; // 实际上是一个空类型因为没有值同时是 red 和 bluelet color: Color; // 无法实例化因为没有值符合 Color 类型8.2 交叉类型的类型成员 交叉类型的成员类型必须符合所有成员类型的属性。 示例 interface A {a: string; }interface B {b: number; }type C A B;let c: C {a: Hello,b: 42 };九、交叉类型与联合类型 交叉类型和联合类型可以组合使用以创建更复杂的类型。 示例 interface Dog {bark(): void; }interface Cat {meow(): void; }type DogCat Dog Cat;function getDogCat(): DogCat {return {bark() {console.log(Woof!);},meow() {console.log(Meow!);}}; }let pet: DogCat getDogCat(); pet.bark(); // 输出: Woof! pet.meow(); // 输出: Meow!十、索引类型 索引类型允许在泛型中使用动态属性访问。 10.1 索引类型查询 使用 keyof 操作符获取一个类型的键的联合类型。 示例 interface Person {name: string;age: number;address: string; }type PersonKeys keyof Person; // name | age | address10.2 索引访问类型 使用索引访问类型获取某个属性的类型。 示例 type NameType Person[name]; // string type AgeType Person[age]; // number10.3 索引类型的应用 结合泛型和索引类型实现更灵活的类型操作。 示例 function getPropertyT, K extends keyof T(obj: T, key: K): T[K] {return obj[key]; }let person: Person {name: Bob,age: 25,address: 123 Main St };let name getProperty(person, name); // name 的类型为 string let age getProperty(person, age); // age 的类型为 number十一、映射对象类型 映射对象类型允许动态地创建对象类型基于已有的类型进行转换。 11.1 映射对象类型声明 使用 in 关键字和 keyof 操作符来声明映射对象类型。 示例 type ReadonlyPerson {readonly [K in keyof Person]: Person[K] };let readonlyPerson: ReadonlyPerson {name: Charlie,age: 30,address: 456 Elm St };// readonlyPerson.age 31; // 错误: 属性 age 是只读的11.2 映射对象类型解析 映射对象类型通过遍历键并应用转换函数来生成新的类型。 示例 type StringifyT {[K in keyof T]: string; };type StringifiedPerson StringifyPerson;let stringifiedPerson: StringifiedPerson {name: Dave,age: 25,address: 789 Oak St };11.3 映射对象类型的应用 结合泛型和映射对象类型实现更复杂的类型操作。 示例 // 定义一个泛型函数将对象的属性值转换为字符串 function stringifyValuesT(obj: T): { [K in keyof T]: string } {let result {} as { [K in keyof T]: string };for (let key in obj) {result[key] String(obj[key]);}return result; }let person: Person {name: Eve,age: 22,address: 321 Pine St };let stringifiedPerson stringifyValues(person); // stringifiedPerson 的类型为 { name: string; age: string; address: string }十二、同态映射对象类型 同态映射对象类型是指在映射过程中保持原有类型的结构。 示例 // 定义一个泛型函数创建一个只读版本的映射对象类型 function makeReadonlyT(obj: T): { readonly [K in keyof T]: T[K] } {return Object.freeze(obj); }let person: Person {name: Frank,age: 28,address: 654 Cedar St };let readonlyPerson makeReadonly(person); // readonlyPerson 的属性是只读的 // readonlyPerson.age 29; // 错误: 属性 age 是只读的总结 TypeScript 的泛型与类型操作提供了强大的工具使得开发者能够编写灵活、可复用的代码。通过理解和掌握这些概念可以显著提升代码质量和开发效率。 案例代码汇总 以下是上述各个部分的完整代码示例 // 泛型函数 function identityT(arg: T): T {return arg; }let output identitynumber(42); let output2 identity(Hello, TypeScript!);// 泛型约束 interface Lengthwise {length: number; }function loggingIdentityT extends Lengthwise(arg: T): T {console.log(arg.length);return arg; }// 泛型接口 interface PairK, V {key: K;value: V; }let user: Pairstring, number {key: age,value: 30 };// 泛型类型别名 type ContainerT T[] | { value: T };let numberContainer: Containernumber [1, 2, 3]; let stringContainer: Containerstring { value: Hello };// 泛型类 class StackT {private elements: T[] [];push(element: T) {this.elements.push(element);}pop(): T | undefined {return this.elements.pop();}peek(): T | undefined {return this.elements[this.elements.length - 1];} }let numberStack new Stacknumber(); numberStack.push(1); numberStack.push(2); console.log(numberStack.peek());let stringStack new Stackstring(); stringStack.push(a); stringStack.push(b); console.log(stringStack.peek());// 局部类型 function processT(value: T) {type Wrapped { wrapped: T };let wrappedValue: Wrapped { wrapped: value };console.log(wrappedValue); }process(Hello);// 联合类型 function printId(id: number | string) {console.log(ID:, id); }printId(101); printId(202);// 联合类型字面量 type Direction left | right | up | down;function move(direction: Direction) {console.log(Moving, direction); }move(left);// 交叉类型 interface Person {name: string; }interface Employee {employeeId: number; }type PersonEmployee Person Employee;let personEmployee: PersonEmployee {name: Alice,employeeId: 123 };// 索引类型 interface Person {name: string;age: number;address: string; }type PersonKeys keyof Person;function getPropertyT, K extends keyof T(obj: T, key: K): T[K] {return obj[key]; }let person: Person {name: Bob,age: 25,address: 123 Main St };let name getProperty(person, name); let age getProperty(person, age);// 映射对象类型 type ReadonlyPerson {readonly [K in keyof Person]: Person[K] };let readonlyPerson: ReadonlyPerson {name: Charlie,age: 30,address: 456 Elm St };// 映射对象类型解析 type StringifyT {[K in keyof T]: string; };type StringifiedPerson StringifyPerson;let stringifiedPerson: StringifiedPerson {name: Dave,age: 25,address: 789 Oak St };// 映射对象类型的应用 function stringifyValuesT(obj: T): { [K in keyof T]: string } {let result {} as { [K in keyof T]: string };for (let key in obj) {result[key] String(obj[key]);}return result; }let person: Person {name: Eve,age: 22,address: 321 Pine St };let stringifiedPerson2 stringifyValues(person);// 同态映射对象类型 function makeReadonlyT(obj: T): { readonly [K in keyof T]: T[K] } {return Object.freeze(obj); }let person2: Person {name: Frank,age: 28,address: 654 Cedar St };let readonlyPerson2 makeReadonly(person2);
http://www.pierceye.com/news/232850/

相关文章:

  • 河南城乡住房和建设厅网站公司微信网站建设方案模板下载
  • 西安制作公司网站的公司邯郸市三建建筑公司网址
  • 网站建设工作目标惠州网站网站建设
  • 就业创业网站建设微信app下载安装旧版本
  • 沧州网站备案年栾洪全单页做网站教程
  • 网站开发的疑虑做门窗投标网站
  • 小型企业门户网站源码如何使用wordpress制作网站
  • 深圳网络营销网站建设北京建设网证书查询平台官网
  • 广播电台网站建设板块自己做网站导航页
  • 网站ui设计兼职android开发工具箱
  • 网站导航网站开发建设公司自己的网站
  • 网站建设专业的公司哪家好优秀创意网站
  • wordpress 文件目录seo网站关键词排名软件
  • 网站管理员功能wordpress增加购物车
  • 外国广告公司网站一个wordpress的爱好者
  • 锦溪网站建设怎么查看网站是否被收录
  • 网站建设感悟平面设计在哪里接单
  • 网站建设中html网页软件开发定制外包服务商
  • 山东seo网站推广河南定制网站建设企业
  • 网站建设文献文档单产品网站建设
  • 唐山网站建设自主开发宁波北仑做公司网站
  • 廊坊网页模板建站专业网站建设公司排名
  • 广州本地生活appseo百度百科
  • 成都产品网站建设镜像网站是怎么做的
  • 网站建设需求分析范例中国建设信息网站
  • 提供网站建设工具的品牌如何自己开个网站平台
  • 站长工具seo综合查询怎么去掉百家号查询排名数据查询
  • 网站怎么做商家定位注册网站不用手机短信验证的网站
  • 郑州医疗网站建设线下推广团队
  • 合肥网站推广 公司哪家好阿里云注销网站