ts中的特殊符号说明并举例,如 ?. 、?:、??等

1. ?. --- 可选链(Optional Chaining)

安全访问深层属性,如果中间任意一层为 nullundefined,直接返回 undefined 而不报错。

ts 复制代码
const name = user?.profile?.name;

// 传统写法等价于:
const name = user && user.profile && user.profile.name;

// 用于方法调用
obj?.method?.();

2. ?? --- 空值合并运算符(Nullish Coalescing)

当左侧值为 nullundefined 时,使用右侧默认值。与 || 的区别在于 || 会把 0''false 也视为假值。

ts 复制代码
const a = null ?? 'default';    // 'default'
const b = 0 ?? 'default';       // 0(0 不是 null/undefined)
const c = '' ?? 'default';      // ''(空字符串不是 null/undefined)
const d = false ?? true;        // false

// 对比 || 的行为:
const e = 0 || 'default';       // 'default'(0 被视为假值)

3. ?. + ?? 组合使用

ts 复制代码
const name = user?.profile?.name ?? '匿名用户';

4. ?. --- 可选元素访问(Optional Element Access)

用于可能不存在的数组索引。

ts 复制代码
const arr: (string | undefined)[] = ['a', 'b'];
const item = arr?.[5]; // undefined,不会报错

5. ?. --- 可选调用(Optional Call)

仅在函数存在时才调用。

ts 复制代码
const fn: (() => void) | undefined = condition ? () => {} : undefined;
fn?.(); // 如果 fn 是 undefined,不会报错

6. ! --- 非空断言(Non-null Assertion)

断言表达式结果不为 nullundefined,告诉 TypeScript 编译器"我保证这里有值"。使用时要确保确实有值,否则运行时可能出错。

ts 复制代码
const el = document.getElementById('app')!; // 断言一定存在
const name = user!.profile!.name;

7. ??= --- 逻辑空赋值(Logical Nullish Assignment)

仅在值为 nullundefined 时才赋值。

ts 复制代码
let x: number | null = null;
x ??= 10;  // x 变为 10

let y: number | null = 5;
y ??= 10;  // y 保持 5,因为不是 null/undefined

8. ?.= --- 可选链赋值(Optional Chaining Assignment,ES2021)

通过可选链访问并赋值。

ts 复制代码
obj?.prop = 'value';
// 等价于:if (obj) { obj.prop = 'value'; }

9. ||= --- 逻辑或赋值(Logical OR Assignment)

在值为假值nullundefined0''falseNaN)时赋值。

ts 复制代码
let x = 0;
x ||= 10; // x 变为 10(0 是假值)

10. &&= --- 逻辑与赋值(Logical AND Assignment)

仅当当前值为真值时才赋值。

ts 复制代码
let x = 'hello';
x &&= 'world'; // x 变为 'world'

let y: string | null = null;
y &&= 'world'; // y 保持 null

11. ... --- 展开运算符(Spread Operator)

对象展开:

ts 复制代码
const a = { x: 1, y: 2 };
const b = { ...a, z: 3 }; // { x: 1, y: 2, z: 3 }

数组展开:

ts 复制代码
const arr1 = [1, 2];
const arr2 = [3, 4];
const merged = [...arr1, ...arr2]; // [1, 2, 3, 4]

函数参数展开:

ts 复制代码
const nums = [1, 2, 3];
Math.max(...nums); // 3

剩余参数:

ts 复制代码
function fn(a: string, ...rest: number[]) {
    console.log(a, rest); // 'hi', [1, 2, 3]
}
fn('hi', 1, 2, 3);

12. ... --- 剩余属性(Rest Properties)

ts 复制代码
const { x, ...remaining } = { x: 1, y: 2, z: 3 };
// x = 1, remaining = { y: 2, z: 3 }

13. : --- 类型注解(Type Annotation)

声明变量、函数参数、返回值的类型。

ts 复制代码
const name: string = 'Tom';
function add(a: number, b: number): number {
    return a + b;
}

14. as --- 类型断言(Type Assertion)

强制告诉编译器某个值的具体类型。

ts 复制代码
const value: unknown = 'hello';
const str = value as string;

// 在 JSX 中需用 <>
const el = document.getElementById('app') as HTMLElement;

15. keyof --- 索引类型查询(Index Type Query)

获取类型的所有属性名组成的联合类型。

ts 复制代码
type User = { name: string; age: number };
type UserKeys = keyof User; // 'name' | 'age'

function getProperty<T, K extends keyof T>(obj: T, key: K): T[K] {
    return obj[key];
}

16. typeof --- 类型查询

获取变量的类型。

ts 复制代码
const config = { theme: 'dark', lang: 'zh' };
type Config = typeof config; // { theme: string; lang: string }

17. infer --- 条件类型中的类型推断

在条件类型中推断某个类型的位置。

ts 复制代码
// 提取数组元素的类型
type ElementType<T> = T extends (infer U)[] ? U : never;
type A = ElementType<string[]>; // string

// 提取函数返回值的类型
type ReturnType<T> = T extends (...args: any[]) => infer R ? R : never;

18. & --- 交叉类型(Intersection Types)

合并多个类型。

ts 复制代码
type A = { x: number };
type B = { y: string };
type C = A & B; // { x: number; y: string }

19. | --- 联合类型(Union Types)

表示值可以是多种类型之一。

ts 复制代码
let id: string | number;
id = 'abc';   // OK
id = 123;     // OK
id = true;    // Error

20. readonly --- 只读修饰符

防止属性被修改。

ts 复制代码
type Point = {
    readonly x: number;
    readonly y: number;
};

const p: Point = { x: 1, y: 2 };
p.x = 5; // Error: Cannot assign to 'x' because it is a read-only property

21. # --- 私有字段(Private Class Fields)

ES2020 / TypeScript 3.8 引入的真正私有字段,比 private 更严格,无法在类外访问,也无法被子类访问。

ts 复制代码
class Counter {
    #count: number = 0; // 真正的私有字段

    inc() {
        this.#count++;
    }

    getValue() {
        return this.#count;
    }
}

const c = new Counter();
c.#count; // Error: Private field '#count' must be declared in an enclosing class

22. asserts --- 断言函数(Assertion Functions)

断言函数确保在返回时某个条件必定成立。

ts 复制代码
function assertIsString(val: unknown): asserts val is string {
    if (typeof val !== 'string') {
        throw new Error('Not a string!');
    }
}

function process(val: unknown) {
    assertIsString(val);
    // 此后 val 被断言为 string,TS 允许直接当作字符串使用
    console.log(val.toUpperCase());
}

23. satisfies --- 满足类型断言(satisfies Operator)

TypeScript 4.9 引入,验证值满足类型,同时保留字面量类型(不会拓宽)。

ts 复制代码
type Color = 'red' | 'green' | 'blue';
type Config = { [key: string]: Color | Color[] };

// 不使用 satisfies:palette 被拓宽为 { [key: string]: ... }
const palette = {
    red: [255, 0, 0],
    green: '#00ff00',
} satisfies Config;

// 使用 satisfies:palette.red 的类型被保留为 [255, 0, 0](元组),palette.green 保留为 string
const redComponent = palette.red[0]; // TS 知道是数字

24. declare --- 声明(Declaration)

声明类型而不实现,常用于声明全局变量、模块、命名空间。

ts 复制代码
declare const __DEV__: boolean;
declare module '*.svg' {
    const content: string;
    export default content;
}

25. enum --- 枚举

ts 复制代码
enum Direction {
    Up = 'UP',
    Down = 'DOWN',
}

// 编译后为:
// const Direction = { Up: 'UP', Down: 'DOWN', Up: 'UP', Down: 'DOWN' };
// const Direction = { 0: 'Up', 1: 'Down', Up: 0, Down: 1 };

26. 模板字面量类型(Template Literal Types)

用反引号定义基于字符串字面量的类型。

ts 复制代码
type EventName = 'click' | 'focus' | 'blur';
type Handler = `on${Capitalize<EventName>}`;
// Handler = 'onClick' | 'onFocus' | 'onBlur'

一图总结

符号 名称 用途
?. 可选链 安全访问嵌套属性
?? 空值合并 ?? 仅对 null/undefined 生效
! 非空断言 断言值不为 null/undefined
??= 空值赋值 仅在 null/undefined 时赋值
` =`
&&= 与赋值 在真值时赋值
... 展开/剩余 合并或收集数据
keyof 索引查询 获取类型的所有键
typeof 类型查询 获取变量的类型
infer 类型推断 条件类型中推断类型
& 交叉类型 合并多个类型
as 类型断言 强制转换类型
readonly 只读 防止属性被修改
# 私有字段 真正的类私有成员
asserts 断言函数 断言某条件必定成立
satisfies 满足断言 验证类型且保留字面量
相关推荐
LaughingZhu1 小时前
Product Hunt 每日热榜 | 2026-06-10
前端·人工智能·经验分享·chatgpt·html
打小就很皮...1 小时前
基于 Python + LangChain + React 实现智能发票识别与验真系统实战
前端·react.js·langchain·ocr·发票识别
小此方1 小时前
【别传:Web前端开发(三)】重塑动态视界:JS底层逻辑、数据类型流转与WebAPI交互全景草稿
前端·javascript·交互
粉末的沉淀1 小时前
css:隐藏video标签的下载按钮
前端·css
仰望.1 小时前
vue表格使用 vxe-table 展开行实现产品列表与明细列表
前端·javascript·vue.js·vxe-table
H178535090962 小时前
SolidWorks_基于草图的实体特征14_扫描扭转与控制
前端·人工智能·算法·3d建模·solidworks
万岳科技系统开发2 小时前
骑手配送系统如何支持外卖与跑腿一体化运营
大数据·前端·小程序
雨季mo浅忆2 小时前
Cursor快速实现上传Excel功能
前端·vue3·ai编程
韩曙亮2 小时前
【Flutter】Flutter 编译 Web 网站 ① ( Tomcat 部署 Web 网站 )
前端·flutter·tomcat·web