TypeScript语法
TypeScript语法
Jintypescript 的出现是为 javascript 添加类型约束
- 编写的 ts 代码最终都会编译成 js 代码运行,浏览器不支持直接运行 ts 类型的代码
变量的声明
var/let/const
变量名:数据类型 = 赋值
例如: const hello: string= 'hello world'
数据类型的类别
number
let num1: number = 6;
let num2: number = 0xf00d;
let num3: number = 0b1010;
let num4: number = 0o744;
支持二、八、十六进制
不区分 int 整数 和 double 浮点数
boolean
取值 ture
& false
let isShow: boolean = false;
string
const name: string = 'fantasy'
// 同样也支持模板字符串
const age: number = 18
const info = `name is ${name},age is ${age}`
Array
// 约束数组内容是 string 类型
const arr1 string[] = ['aaa','bbb','ccc']
// 泛型
const arr2 Array<string> = ['ddd','eee','fff']
object
object 可以表述一个对象
const infos: object = {
name: 'fantasy',
age: 18
}
// 输出 fantasy
console.log(infos.name)
// 不能赋值 error
infos.age=20
symbol
// symbol来定义相同的名称,Symbol函数返回的是不同的值
const s1: symbol = Symbol("title")
const s2: symbol = Symbol("title")
cosnt person = {
[s1]: '医生',
[s2]: '护士'
}
null & undefined
undefined和null两者各自有自己的类型分别叫做undefined和null
它们的本身的类型用处不是很大
let u: undefined = undefined;
let n: null = null;
any
无法确定一个变量的类型,并且可能它会发生变化,可以使用any类型
let id: any = 123
// 可以赋值任意类型 相当于回到JS
id = '123'
id = ['123']
id = {name: fantasy}
void
某种程度上来说,void类型像是与any类型相反,它表示没有任何类型。 当一个函数没有返回值时,返回值类型为 void
function hello(): void {
console.log('hello world')
}
声明一个void类型的变量没有什么用,只能为它赋予undefined和null
never
never类型表示的是那些永不存在的值的类型。
例如,函数一个死循环和抛出一个异常
function loop(): never{
while(true){
console.log('hello')
}
}
function errorFn(): never{
throw new Error()
}
Tuple
元组类型允许表示一个已知元素数量和类型的数组,各元素的类型不必相同
let arr: [string,number] = ['name',18]
// string 可以运行
console.log(arr[0].substr(1))
// number 报错 error
console.log(arr[1].substr(1))
// 可以越界,类型为上面其中一种
arr[2] = 'hello'
函数的类型
参数
声明函数时,在每个参数后添加类型注解,以声明函数接受的参数类型
function foo(name: string,age: number){
console.log(name,age)
}
返回值
注解出现在函数列表的后面
function(num1: number,num2: number): number{
return num1+num2
}
匿名函数
当函数出现在TypeScript可以确定该函数会被如何调用的地方时,参数会自动指定类型
const lists = ['aaa','bbb','ccc']
lists.forEach(item=>{
console.log(item.toUpperCase())
})
上下文类型(contextual typing)可以帮助确定参数和返回值的类型
即TypeScript会根据forEach函数的类型以及数组的类型推断出item的类型
变量的类型推导
开发中并不会在声明每一个变量时都写上对应的数据类型
TypeScript本身的可以特性帮助我们推断出对应的变量类型
let str = 'hello'
// 报错 error
// 变量第一次赋值时,根据赋值内容的类型,推断类型
str = 123
联合类型
- 联合类型表示由多个类型组成
- 表示可以是多个类型中任意一个类型
- 类型中每一个类型被称为联合成员
function foo(id: number|string ){
// 如需要根据类型使用
// 进行类型缩小
if(typeof id === string){
console.log(id.toUpperCase())
}else
console.log(id)
}
foo("abc")
foo(123)
type类型别名
为了类型注解可以方便多次使用可以类型别名
type infosType = {
name: string
age: number
}
function foo(infos: infosType){
console.log('名字',infos.name,'年龄',infos.age)
}
foo({name: 'jay' ,age: 18})
interface接口
接口用来声明对象类型,与type别名大致相同
interface Iinfos {
name: string,
age: number
}
function foo(infos: Iinfos){
console.log('名字',infos.name,'年龄',infos.age)
}
type & interface 区别
- 如果是定义非对象类型,通常推荐使用type
- interface可以重复定义某一个的接口的属性和方法
- type定义的是别名,别名是不能重复
interface Iinfo {
name: string
run: ()=>void
}
// 重复定义 这是运行的
// 如用type声明会error
interface Iinfo {
age: number
}
交叉类型
交叉类型表示同时满足多个条件
通常应用于对象类型交叉
interface Iinfo {
name: string
age: number
}
interface IRun {
run: ()=>void
}
const person: Iinfo&IRun = {
name:'jay',
age: 18,
run: function(){
console.log('running')
}
}
类型断言
某种情况TypeScript无法获取具体的类型信息,需要使用类型断言
as : 类型
const myimg = document.getElementById('pic') as HTMLImageElement
myimg.src='/图片地址'
非空断言
非空断言使用的是 !
,表示可以确定某个标识符是有值的,跳过ts在编译阶段对它的检测
function foo(msg?: string){
// error 值可能是undefined
console.log(msg.toUpperCase())
// 如确保有类型 使用非空短言
console.log(msg!.toUpperCase())
}
字面量类型
如:
let msg: 'hello' ='hello'
// 报错,你好 类型不是 hello
msg='你好'
用 const 声明的常量默认是字面量类型
默认情况这样作意义不大
搭配联合类型使用
type positionType = 'left' | 'right' | 'up' | 'down'
function changePosition(position: positionType){
console.log('修改反向:',position)
}
changePosition('left')
字面量推理
const info ={
url: "https://127.0.0.1"
method: "GET"
}
function Myrequest(url: string, method: 'GET'|'POST'){
console.log(url,method)
}
// 调用会报错,inof.method不是字面量类型
// 因为字面量推理会得出 info其实是一个 {url: string, method: string}
Myrequest(info.url,info.method)
// 解决方法 使用类型断言
// 方法一 调用时使用
Myrequest(info.url,info.method as 'GET')
// 方法二 对象上使用
const info ={
url: "https://127.0.0.1"
method: "GET"
} as const
类型缩小
- 通过类似于
typeof padding === "number"
的判断语句,来改变TypeScript的执行路径 - 给定的执行路径中,我们可以缩小比声明时更小的类型,这个过程称之为 缩小( Narrowing )
- 我们编写的 typeof padding === “number 可以称之为 类型保护(type guards)
常见的类型保护:typeof
、===,!==
、instanceof
、in
// typeof
type idType = string | number
function foo(id: idType){
if(id typeof string){
console.log("string:",id)
}else
{
console.log("number:",id)
}
}
// === !==
type positionType = 'left' | 'right'
function changePosition(position: positionType){
if(position==='left'){
console.log('change left')
}else {
console.log('change right')
}
}
// instanceof 检查一个值是不是另一个值的实例
function outputDate(date: Date|string){
// 判断date算不算 Date 的实例
if(data instanceof Date){
console.log(date.toLocaleString())
} else{
console.log(date)
}
}
// in 指定的属性在指定的对象或其原型链中,则in 运算符返回true
type fish = {swim:()=>void}
type kun = {rap:()=>void}
function move(animal: fish|kun){
if('swim' in animal){
console.log('swimming')
}else{
console.log('唱 跳 rap')
}
}
参考资料