as count
是对字面值的断言,与const直接定义常量是有区别的。
定义常量的时候是限制了变量的指针无法修改,但是对象类型还是可以做数据的修改,因为此时只修改了指针指向的内存空间的数据。而一旦使用了as const
断言后,此时变量只能为当前值,无法做任何的修改。
针对string
、number
、null
等非对象类型
// 效果是一致的,常量都无法修改
const a = 'hello';
let b = 'hello' as const;
a = 'world'; // 错误
b = 'world'; // 错误
针对Array
、Object
// 数组
let arr1 = [10, 20] as const;
const arr2 = [10, 20];
arr1.push(30); // 错误,此时已经断言字面量为[10, 20],数据无法做任何修改
arr2.push(30); // 通过,没有修改指针
let obj1 = {
name: 'zhangsan',
age: 3
} as const;
const obj2 = {
name: 'zhangsan',
age: 3
};
obj1.name = 'lisi'; // 错误,无法修改字段
obj2.name = 'lisi'; // 通过
推断场景
断言会在类型推断是得知具体值和类型,同时能推断出length等
// 无报错
const args = [10, 20] as const; // 断言args为[10, 20]
// const args: readonly [10, 20]
const angle = Math.atan2(...args); // 通过上面断言,得知args.length为2,函数接受两个参数,不会报错
console.log(angle);
// 会报错,此时只知道args是number数组,无法确定里面有多少个元素,所有atan2无法确定得到两个参数而报错
const args = [10, 20];
// const args: number[]
const angle = Math.atan2(...args); // error! Expected 2 arguments, but got 0 or more.
console.log(angle);
readonly
只读只是处理了字段无法再修改,不会断言出其他属性,例如length:
let args: readonly number[];
args = [10, 20];
const angle = Math.atan2(...args); // A spread argument must either have a tuple type or be passed to a rest parameter.(2556)