TypeScript 基础笔记
- 安装TypeScript
- 编译ts
- Typescript 开发工具 Vscode 自动编译.ts 文件
- 数据类型
- 布尔类型(boolean)
- 数字类型(number)
- 字符串类型(string)
- 数组类型(array) ts中定义数组有两种方式
- 元组类型(tuple) 属于数组的一种
- 枚举类型(enum)
- 任意类型(any)
- null 和 undefined 其他(never类型)数据类型的子类型
- void类型
- never类型 是其他类型 (包括 null 和 undefined)的子类型,代表从不会出现的值
- typeScript中的函数
- 函数的定义
- 可选参数
- 默认参数
- 剩余参数
- 函数重载
- 箭头函数 es6
- es5创建对象 继承
- typeScript中的类
- ts中类的定义
- 2、ts中实现继承 extends、 super
- ts中继承的探讨 父类的方法和子类的方法一致,调用子类的方法
- 类里面的修饰符 typescript里面定义属性的时候给我们提供了 三种修饰符
- public :公有 在类里面、 子类 、类外面都可以访问
- protected:保护类型 在类里面、子类里面可以访问,在类外部没法访问
- private :私有 在类里面可以访问,子类、类外部都没法访问
- typeScript中的泛型
- 泛型的定义
- 泛型函数
- 泛型类
- 泛型接口
安装TypeScript
npm install -g typescript
编译ts
tsc ts文件
Typescript 开发工具 Vscode 自动编译.ts 文件
vscode配置自动编译
1.第一步 tsc --inti 生成tsconfig.json 改 "outDir": "./js",
2、第二步 任务 - 运行任务 监视tsconfig.json
数据类型
布尔类型(boolean)
let flag:boolean=true;
数字类型(number)
let num:number=123;
字符串类型(string)
let str:string='this is ts';
数组类型(array) ts中定义数组有两种方式
// 1.第一种定义数组的方式
let arr:number[]=[11,22,33];
console.log(arr);
//2.第二种定义数组的方式
let arr:Array<number>=[11,22,33];
元组类型(tuple) 属于数组的一种
let arr:[number,string]=[123,'this is ts'];
枚举类型(enum)
<!--enum 枚举名{
标识符[=整型常数],
标识符[=整型常数],
...
标识符[=整型常数],
} ; -->
enum Flag {success=1,error=2};
let s:Flag=Flag.success;
// enum Color {blue,red,'orange'};
// var c:Color=Color.red;
// console.log(c); //1 如果标识符没有赋值 它的值就是下标
任意类型(any)
var num:any=123;
//任意类型的用处
var oBox:any=document.getElementById('box');
oBox.style.color='red';
null 和 undefined 其他(never类型)数据类型的子类型
// var num:number;
// console.log(num) //输出:undefined 报错
// var num:undefined;
// console.log(num) //输出:undefined //正确
// var num:number | undefined;
// num=123;
// console.log(num);
//一个元素可能是 number类型 可能是null 可能是undefined
var num:number | null | undefined;
void类型
//表示方法没有返回任何类型
function run():void{
console.log('run')
}
run();
function run():number{
return 123;
}
run();
never类型 是其他类型 (包括 null 和 undefined)的子类型,代表从不会出现的值
//这意味着声明never的变量只能被never类型所赋值。
var a:never;
// a=123; //错误的写法
a=(()=>{
throw new Error('错误');
})()
typeScript中的函数
函数的定义
//函数声明法
function run():string{
return 'run';
}
//匿名函数
var fun2=function():number{
return 123;
}
alert(fun2()); /*调用方法*/
//ts中定义方法传参
function getInfo(name:string,age:number):string{
return `${name} --- ${age}`;
}
alert(getInfo('zhangsan',20));
//没有返回值的方法
function run():void{
console.log('run')
}
run();
可选参数
// es5里面方法的实参和行参可以不一样,但是ts中//必须一样,如果不一样就需要配置可选参数
function getInfo(name:string,age?:number):string{
if(age){
return `${name} --- ${age}`;
}else{
return `${name} ---年龄保密`;
}
}
alert(getInfo('zhangsan'))
alert(getInfo('zhangsan',123))
//注意:可选参数必须配置到参数的最后
//错误写法
function getInfo(name?:string,age:number):string{
if(age){
return `${name} --- ${age}`;
}else{
return `${name} ---年龄保密`;
}
}
alert(getInfo('zhangsan'))
默认参数
// es5里面没法设置默认参数,es6和ts中都可以设置默认参数
function getInfo(name:string,age:number=20):string{
if(age){
return `${name} --- ${age}`;
}else{
return `${name} ---年龄保密`;
}
}
// alert( getInfo('张三'));
alert( getInfo('张三',30));
剩余参数
function sum(a:number,b:number,c:number,d:number):number{
return a+b+c+d;
}
alert(sum(1,2,3,4));
//三点运算符 接受新参传过来的值
function sum(...result:number[]):number{
var sum=0;
for(var i=0;i<result.length;i++){
sum+=result[i];
}
return sum;
}
alert(sum(1,2,3,4,5,6)) ;
function sum(a:number,b:number,...result:number[]):number{
var sum=a+b;
for(var i=0;i<result.length;i++){
sum+=result[i];
}
return sum;
}
alert(sum(1,2,3,4,5,6)) ;
函数重载
// java中方法的重载:重载指的是两个或者两个以上同名函数,但它们的参数不一样,这时会出现函数重载的情况。
// typescript中的重载:通过为同一个函数提供多个函数类型定义来试下多种功能的目的。
//ts为了兼容es5 以及 es6 重载的写法和java中有区别。
//es5中出现同名方法,下面的会替换上面的方法
function css(config){
}
function css(config,value){
}
//ts中的重载 通过为同一个函数提供多个函数类型定义来试下多种功能的目的。
function getInfo(name: string): string;
function getInfo(age: number): string;
function getInfo(age: Array<number>): string;
function getInfo(str: any): any {
if (typeof str === 'string') {
return '我叫:' + str;
} else {
return '我的年龄是' + str;
}
}
alert(getInfo('张三')); //正确
alert(getInfo(20)); //正确
alert(getInfo([1])); //正确
alert(getInfo(true)); //错误写法
function getInfo(name:string):string;
function getInfo(name:string,age:number):string;
function getInfo(name:any,age?:any):any{
if(age){
return '我叫:'+name+'我的年龄是'+age;
}else{
return '我叫:'+name;
}
}
alert(getInfo('zhangsan')); /*正确*/
alert(getInfo('zhangsan',20));
alert(getInfo(123)); //错误
箭头函数 es6
//this指向的问题 箭头函数里面的this指向上下文
setTimeout(()=>{
alert('run')
},1000)
es5创建对象 继承
// es5里面的类
//1.最简单的类
function Person() {
this.name = "张三";
this.age = 20;
}
var p = new Person();
alert(p.name);
//2、构造函数和原型链里面增加方法
function Person() {
this.name = "张三"; /*属性*/
this.age = 20;
this.run = function() {
alert(this.name + "在运动");
};
}
// //原型链上面的属性会被多个实例共享 构造函数不会
Person.prototype.sex = "男";
Person.prototype.work = function() {
alert(this.name + "在工作");
};
var p = new Person();
// alert(p.name);
// p.run();
p.work();
//3类里面的静态方法
function Person() {
this.name = "张三"; /*属性*/
this.age = 20;
this.run = function() {
/*实例方法*/
alert(this.name + "在运动");
};
}
Person.getInfo = function() {
alert("我是静态方法");
};
//原型链上面的属性会被多个实例共享 构造函数不会
Person.prototype.sex = "男";
Person.prototype.work = function() {
alert(this.name + "在工作");
};
var p = new Person();
p.work();
//调用静态方法
Person.getInfo();
// 4、es5里面的继承 对象冒充实现继承
function Person() {
this.name = "张三"; /*属性*/
this.age = 20;
this.run = function() {
/*实例方法*/
alert(this.name + "在运动");
};
}
Person.prototype.sex = "男";
Person.prototype.work = function() {
alert(this.name + "在工作");
};
//Web类 继承Person类 原型链+对象冒充的组合继承模式
function Web() {
Person.call(this); /*对象冒充实现继承*/
}
var w = new Web();
// w.run(); //对象冒充可以继承构造函数里面的属性和方法
w.work(); //对象冒充可以继承构造函数里面的属性和方法 但是没法继承原型链上面的属性和方法
// 5、es5里面的继承 原型链实现继承
function Person() {
this.name = "张三"; /*属性*/
this.age = 20;
this.run = function() {
/*实例方法*/
alert(this.name + "在运动");
};
}
Person.prototype.sex = "男";
Person.prototype.work = function() {
alert(this.name + "在工作");
};
//Web类 继承Person类 原型链+对象冒充的组合继承模式
function Web() {}
Web.prototype = new Person(); //原型链实现继承
var w = new Web();
//原型链实现继承:可以继承构造函数里面的属性和方法 也可以继承原型链上面的属性和方法
//w.run();
w.work();
// 6、 原型链实现继承的 问题?
function Person(name, age) {
this.name = name; /*属性*/
this.age = age;
this.run = function() {
/*实例方法*/
alert(this.name + "在运动");
};
}
Person.prototype.sex = "男";
Person.prototype.work = function() {
alert(this.name + "在工作");
};
var p = new Person("李四", 20);
p.run();
function Person(name, age) {
this.name = name; /*属性*/
this.age = age;
this.run = function() {
/*实例方法*/
alert(this.name + "在运动");
};
}
Person.prototype.sex = "男";
Person.prototype.work = function() {
alert(this.name + "在工作");
};
function Web(name, age) {}
Web.prototype = new Person();
var w = new Web("赵四", 20); //实例化子类的时候没法给父类传参
w.run();
// var w1=new Web('王五',22);
//7.原型链+对象冒充的组合继承模式
function Person(name, age) {
this.name = name; /*属性*/
this.age = age;
this.run = function() {
/*实例方法*/
alert(this.name + "在运动");
};
}
Person.prototype.sex = "男";
Person.prototype.work = function() {
alert(this.name + "在工作");
};
function Web(name, age) {
Person.call(this, name, age); //对象冒充继承 实例化子类可以给父类传参
}
Web.prototype = new Person();
var w = new Web("赵四", 20); //实例化子类的时候没法给父类传参
// w.run();
w.work();
// var w1=new Web('王五',22);
//8、原型链+对象冒充继承的另一种方式
function Person(name, age) {
this.name = name; /*属性*/
this.age = age;
this.run = function() {
/*实例方法*/
alert(this.name + "在运动");
};
}
Person.prototype.sex = "男";
Person.prototype.work = function() {
alert(this.name + "在工作");
};
function Web(name, age) {
Person.call(this, name, age); //对象冒充继承 可以继承构造函数里面的属性和方法、实例化子类可以给父类传参
}
Web.prototype = Person.prototype;
var w = new Web("赵四", 20); //实例化子类的时候没法给父类传参
w.run();
// w.work();
// var w1=new Web('王五',22);
typeScript中的类
ts中类的定义
es5:
function Person(name){
this.name=name; this.run=function(){ console.log(this.name)
}
}
var p=new Person('张三');
p.run()
ts中定义类:
class Person{
name:string; //属性 前面省略了public关键词
constructor(n:string){ //构造函数实例化类的时候触发的方法
this.name=n;
}
run():void{
alert(this.name);
}
getName():string{
return this.name;
}
setName(name:string):void{
this.name=name;
}
}
var p=new Person('张三');
p.run()
2、ts中实现继承 extends、 super
class Person{
name:string;
constructor(name:string){
this.name=name;
}
run():string{
return `${this.name}在运动`
}
}
var p=new Person('王五');
alert(p.run())
class Web extends Person{
constructor(name:string){
super(name); /*初始化父类的构造函数*/
}
}
var w=new Web('李四');
alert(w.run());
ts中继承的探讨 父类的方法和子类的方法一致,调用子类的方法
class Person{
name:string;
constructor(name:string){
this.name=name;
}
run():string{
return `${this.name}在运动`
}
}
// var p=new Person('王五');
// alert(p.run())
class Web extends Person{
constructor(name:string){
super(name); /*初始化父类的构造函数*/
}
run():string{
return `${this.name}在运动-子类`
}
work(){
alert(`${this.name}在工作`)
}
}
var w=new Web('李四');
// alert(w.run());
// w.work();
alert(w.run()); // 李四在运动-子类
类里面的修饰符 typescript里面定义属性的时候给我们提供了 三种修饰符
public :公有 在当前类里面、 子类 、类外面都可以访问
protected:保护类型 在当前类里面、子类里面可以访问,在类外部没法访问
private :私有 在当前类里面可以访问,子类、类外部都没法访问
public :公有 在类里面、 子类 、类外面都可以访问
class Person{
public name:string; /*公有属性*/
constructor(name:string){
this.name=name;
}
run():string{
return `${this.name}在运动`
}
}
var p=new Person('王五');
alert(p.run())
class Web extends Person{
constructor(name:string){
super(name); /*初始化父类的构造函数*/
}
run():string{
return `${this.name}在运动-子类`
}
work(){
alert(`${this.name}在工作`)
}
}
var w=new Web('李四');
w.work();
//类外部访问公有属性
class Person{
public name:string; /*公有属性*/
constructor(name:string){
this.name=name;
}
run():string{
return `${this.name}在运动`
}
}
var p=new Person('哈哈哈');
alert(p.name);
protected:保护类型 在类里面、子类里面可以访问,在类外部没法访问
class Person {
protected name: string; /*公有属性*/
constructor(name: string) {
this.name = name;
}
run(): string {
return `${this.name}在运动`
}
}
var p = new Person('王五');
alert(p.run())
alert(p.name) // 报错
class Web extends Person {
constructor(name: string) {
super(name); /*初始化父类的构造函数*/
}
work() {
alert(`${this.name}在工作`)
}
}
var w = new Web('李四11');
w.work();
alert(w.run());
//类外外部没法访问保护类型的属性
class Person{
protected name:string; /*保护类型*/
constructor(name:string){
this.name=name;
}
run():string{
return `${this.name}在运动`
}
}
var p=new Person('哈哈哈');
alert(p.name);
private :私有 在类里面可以访问,子类、类外部都没法访问
class Person{
private name:string; /*私有*/
constructor(name:string){
this.name=name;
}
run():string{
return `${this.name}在运动`
}
}
class Web extends Person{
constructor(name:string){
super(name)
}
work(){
console.log(`${this.name}在工作`) // 报错
}
}
class Person{
private name:string; /*私有*/
constructor(name:string){
this.name=name;
}
run():string{
return `${this.name}在运动`
}
}
var p=new Person('哈哈哈');
alert(p.run());
typeScript中的泛型
泛型的定义
泛型:软件工程中,我们不仅要创建一致的定义良好的API,同时也要考虑可重用性。 组件不仅能够支持当前的数据类型,同时也能支持未来的数据类型,这在创建大型系统时为你提供了十分灵活的功能。
在像C#和Java这样的语言中,可以使用泛型来创建可重用的组件,一个组件可以支持多种类型的数据。 这样用户就可以以自己的数据类型来使用组件。
通俗理解:泛型就是解决 类 接口 方法的复用性、以及对不特定数据类型的支持(类型校验)
//只能返回string类型的数据
function getData(value:string):string{
return value;
}
//同时返回 string类型 和number类型 (代码冗余)
function getData1(value:string):string{
return value;
}
function getData2(value:number):number{
return value;
}
//同时返回 string类型 和number类型 any可以解决这个问题
function getData(value:any):any{
return '哈哈哈';
}
getData(123);
getData('str');
//any放弃了类型检查,传入什么 返回什么。比如:传入number 类型必须返回number类型 传入 string类型必须返回string类型
//传入的参数类型和返回的参数类型可以不一致
// function getData(value:any):any{
// return '哈哈哈';
// }
泛型函数
泛型:可以支持不特定的数据类型 要求:传入的参数和返回的参数一直
// T表示泛型,具体什么类型是调用这个方法的时候决定的
function getData<T>(value:T):T{
return value;
}
getData<number>(123);
getData<string>('1214231');
getData<number>('2112'); /*错误的写法*/
function getData<T>(value:T):any{
return '2145214214';
}
getData<number>(123); //参数必须是number
getData<string>('这是一个泛型');
泛型类
//泛型类:比如有个最小堆算法,需要同时支持返回数字和字符串 a - z两种类型。 通过类的泛型来实现
class MinClass{
public list:number[]=[];
add(num:number){
this.list.push(num)
}
min():number{
var minNum=this.list[0];
for(var i=0;i<this.list.length;i++){
if(minNum>this.list[i]){
minNum=this.list[i];
}
}
return minNum;
}
}
var m=new MinClass();
m.add(3);
m.add(22);
m.add(23);
m.add(6);
m.add(7);
alert(m.min());
//类的泛型
class MinClas<T>{
public list:T[]=[];
add(value:T):void{
this.list.push(value);
}
min():T{
var minNum=this.list[0];
for(var i=0;i<this.list.length;i++){
if(minNum>this.list[i]){
minNum=this.list[i];
}
}
return minNum;
}
}
var m1=new MinClas<number>(); /*实例化类 并且制定了类的T代表的类型是number*/
m1.add(11);
m1.add(3);
m1.add(2);
alert(m1.min())
var m2=new MinClas<string>(); /*实例化类 并且制定了类的T代表的类型是string*/
m2.add('c');
m2.add('a');
m2.add('v');
alert(m2.min())
泛型接口
//函数类型接口
interface ConfigFn{
(value1:string,value2:string):string;
}
var setData:ConfigFn=function(value1:string,value2:string):string{
return value1+value2;
}
setData('name','张三');
//1、泛型接口
interface ConfigFn{
<T>(value:T):T;
}
var getData:ConfigFn=function<T>(value:T):T{
return value;
}
// getData<string>('张三');
// getData<string>(1243); //错误
//2、泛型接口
interface ConfigFn<T>{
(value:T):T;
}
function getData<T>(value:T):T{
return value;
}
var myGetData:ConfigFn<string>=getData;
myGetData('20'); /*正确*/
// myGetData(20) //错误