TypeScript 变量声明详解
TypeScript 的变量声明方式与现代 JavaScript(ES6+)完全一致,主要使用 let、const 和 var(不推荐)。区别在于 TypeScript 增加了静态类型注解,可以在声明时指定变量的类型,从而在编译阶段捕获错误。
1. 基本声明关键字
| 关键字 | 作用域 | 是否可重新赋值 | 是否可重新声明 | 推荐场景 |
|---|---|---|---|---|
const | 块级作用域 | 不可 | 不可 | 常量、不会改变的值 |
let | 块级作用域 | 可 | 不可 | 需要重新赋值的变量 |
var | 函数作用域(或全局) | 可 | 可 | 不推荐(易导致 bug) |
2. 声明语法与类型注解
基本格式:
// 无类型注解(依靠类型推断)
let variableName = value;
// 带类型注解
let variableName: type = value;
// const 同理
const constantName: type = value;
示例对比
// 1. const(推荐用于不变值)
const PI: number = 3.14159; // 显式类型注解
const username = "Alice"; // 类型推断为 string(推荐,简洁)
// username = "Bob"; // 错误:const 不可重新赋值
// 2. let(用于可变变量)
let age: number = 25; // 显式注解
age = 26; // OK
let score = 100; // 类型推断为 number
score = 200; // OK
// score = "high"; // 错误:类型不匹配
// 3. var(不推荐)
var oldStyle = "legacy";
// oldStyle = 123; // JS 中允许,但 TS 会根据首次赋值推断类型
3. 类型注解的位置与类型推断
- 推荐优先使用类型推断:大多数情况下无需显式写类型,TS 会自动推断。
- 显式注解的场景:
- 初始化值是
null或undefined时。 - 函数参数和返回值。
- 复杂对象、联合类型等。
let name: string; // 声明但未初始化(必须显式类型)
name = "Alice";
let nullable: string | null = null; // 联合类型
let data: any = "anything"; // 关闭类型检查(慎用)
4. 特殊声明方式
a. 解构赋值(Destructuring)
// 数组解构
const [first, second]: [number, number] = [1, 2];
// 对象解构
interface User {
name: string;
age: number;
}
const { name, age }: User = { name: "Bob", age: 30 };
// 部分解构 + 重命名
const { name: userName, age }: { name: string; age: number } = { name: "Charlie", age: 28 };
b. 默认值与可选属性
function greet(name: string = "Guest"): string {
return `Hello ${name}`;
}
greet(); // "Hello Guest"
greet("Dave"); // "Hello Dave"
c. 展开运算符(Spread)
const defaults = { timeout: 1000, retries: 3 };
const config: typeof defaults = { ...defaults, timeout: 5000 };
5. 作用域示例(let vs var)
if (true) {
let blockScoped = "only here"; // 块外不可访问
var functionScoped = "everywhere";
}
console.log(functionScoped); // OK
// console.log(blockScoped); // 错误:未定义
6. 最佳实践建议
- 优先使用
const,需要修改时再改用let。 - 永远不要使用
var(容易造成变量提升和作用域污染)。 - 大多数情况依靠类型推断,只在必要时添加显式类型。
- 开启严格模式(
strict: true),包括noImplicitAny等。 - 对于对象和数组,推荐使用接口或类型别名定义结构。
// 推荐:定义接口后声明变量
interface Point {
x: number;
y: number;
}
const origin: Point = { x: 0, y: 0 };
let position: Point = { x: 10, y: 20 };
小结:常见声明模式速查
| 场景 | 推荐写法 |
|---|---|
| 常量字符串/数字 | const NAME = "Alice"; |
| 可变值 | let count = 0; |
| 明确类型(复杂) | let ids: number[] = []; |
| 对象 | const user: { name: string; age: number } = ... 或使用 interface |
| 可能为空 | let element: HTMLElement | null = null; |
如果您想深入了解函数参数声明、类属性声明、模块内声明或其他高级场景(如声明合并、声明文件 .d.ts),请告诉我!