一、基础部分
1.安装和编译
npm install -g typescript
tsc helloword.ts
2.用VScode 自动编译 .ts
a. 创建tsconfig.json文件。 tsc --init 生成配置文件
b. 任务 - 运行任务,监视tsconfig.json
3.typescript 中的数据类型(ts新增类型校验,ts 代码必须指定类型)
-
布尔类型(boolean)
var flag:boolean=true;
-
数字类型(number)
var num:number=123;
-
字符串类型 (string)
-
数组类型(array)
定义数组的两种方式
a. var arr:number[]=[11,22,33,44] ----- b. var arr:Array<number>=[11,22,33] --- var arr:any[]=[123,'123']
-
元祖类型(tuple)属于数组的一种,为数组每一个位置指定一个类型
let arr:[number,string]=[12,'aa']; let arr:Array<number,string>=[12,'string']
-
枚举类型(enum)
enum Err {'undefined'=-1,'null'=-2,'success'=1};
var e:Err=Err.sucess;
console.log(e) //打印出的为1(如果标识符没赋值,它的值就是下标)
- 任意类型(any)
var num:any=123;
- null 和 undefined
var num:number | null | undefined
- void 类型
//当方法没有返回值时:
function run():void{
console.log('run')
}
//当方法有返回值时:
function run():number {
return 123;
}
- never类型
var a:never;
a=(()=>{
throw new Error('错误');
})()
4. 函数的定义
//函数声明法
function run():string{
return 'run';
}
//匿名函数法
var fun2=function():number{
return 123;
}
//定义方法传参
function getInfo(name:string,age:number):string{
return `${name}--${age}`;
}
//配置可选参数(用?)
function getInfo(name:string,age?:number):string{
return ''
}
getInfo('zhangsan');
//三点运算符,接收传过来的值
function sum(...result:number[]):number{
var sum=0;
for(var i=0;i<result.length;i++){
sum+=result[i]
}
}
//ts中方法的重载
function getInfo(name:string):string;
function getInfo(name:number):number;
function getInfo(str:any):any{
if(typeof str==='string'){
return ''
}else{
return '123'
}
ts中的类
class Person(){
name:string; //属性,前边省略 了public关键词
constructor(n:string){
this.name=n;
}
run():void{
alert(this.name)
}
}
class Person(){
name:string; //属性,前边省略 了public关键词
constructor(n:string){
this.name=n;
}
getName():string{
return this.name;
}
setName(name:string):void{
this.name=name;
}
}
ts中的继承
class Person(){
public name:string; //公有属性
constructor(name:string){
this.name=name;
}
run():string{
return `${this.name}在运动 `
}
}
class Web extends Person{
constructor(name:string){
super(name); //初始化父类的构造函数
}
}
var w=new Web('李四');
alert(w.run();
类里面的修饰符,ts提供了三种修饰符
- public:公有,内外部都可以访问
- protected:保护类型 类内部、子类内部可以访问,类外无法访问
- private:私有 在类内可以访问,子类无法访问。
属性如果不加修饰符,默认为public
静态方法和静态属性
function Person(){
this.run1=function(){} //实例方法,new之后才能用
}
Person.run2(); //静态方法,可以直接用。
class Person(){
public name:string;
public age:number=20;
static sex="男";//静态属性
constructor(name:string){
this.name=name;
}
run(){ //实例方法
alert()
}
static print(){
console.log('print'+this.age) //会出错,静态没法不能直接调用类里的属性
console.log('print'+Person.sex) //不会出错
} //静态方法
}
多态:父类定义一个方法,不去实现。让继承它的子类去实现,每个子类有不同的表现。
比如先定义个ainimal类,里面有eat方法。然后有猫和狗两个子类去继承这个类,然后重写eat的方法。
抽象类:提供其他类继承的基类,不能直接被实例化。
用abstract 关键字定义抽象类和抽象方法,抽象类中的抽象方法不包含具体实现并且必须在派生类中实现。
抽象类和抽象方法用来定义标准,比如:Animal这个类要求它的子类必须包含eat方法。
abstract class Animal{
public name:string;
constructor(name:string){
this.name=name;
}
abstract eat():any;
}
var a=new Animal() //错误写法,抽象类不能直接被实例化。只能给其他类提供基类。
class Dog extends Animal{
constructor(name:any){
super(name);
}
//抽象类的子类必须实现抽象类中的抽象方法
eat(){
console.log('dog)
}
}
接口的作用:在面向对象的编程中,它定义了行为和动作的规范,起到限制和规范的作用。它不关心类的内部状态数据和类里方法的实现细节,只规定这批类里必须提供某些方法。ts中的接口类似java,还增加了更多 接口类型,包括属性函数可索引和类等。
- 属性接口 对json的规范。
function printLabel(labelInfo:{label:string}):void(){
console.log(' ')
}
printLabel({name:'zhangsan'}) //错误
printLabel({label:'zhangsan'}) //正确
- 属性类型接口
interface FullName{ //对传入对象的约束 (属性接口)
firstName:string;
secondName:string;
}
function printName(name:FullName){
}
实例:ajax
interface Config{
type:string;
url:string;
data?:string;
dataType:string
}
function ajax(config:Config){
var xhr=new XMLHttpRequest();
xhr.open(config.type,config.url,true );
xhr.send(config.data);
xhr.onreadystatechange=function(){
if(xhr.readyState==4 && xhr.status==200){
config.log('success');
}
}
}
ajax({
tyle:'get',
url:'http://www.baidu.com,
data:{},
dataType:'JSONP'
})
- 函数类型接口 (对方法传入的参数以及返回值进行约束 )
interface encrypt{
(key:string,value:string):string;
}
var md5:encrypt=function(key:string,value:string):string{
return key+value;
}
- 可索引接口:数组、对象的约束(不常用)
var arr:number[]=[123,123]
var arr1:Array<string>=['123','123']
interface UserArr{
[index:number]:string
}
var arr:UserArr=['aaa','bbb'];
console.log(arr[0 ])
- 类类型的接口(对类的约束)
interface Animal{
name:string;
eat(str:string):void;
}
class Dog implements Animal{
name:string;
constructor(name:string){
this.name=name;
}
eat(){
console.log(this.name + '');
}
}
var d= new Dog();
- 接口的扩展:接口可以继承接口
interface Animal{
eat():void;
}
interface Person extends Animal{
work():void;
}
class Programmer{
public name:string;
constructor(name:string){
this.name=name;
constructor(name:string){
this.name=name;
}
coding(code:string){
console.log('写代码')
}
}
}
class Web extends Programmer implements Person{
public name:string;
constructor(name:string){
super(name)
}
eat(){
console.log()
}
work(){
console.log()
}
}
--- ts中的泛型:就是解决类、接口、方法的复用性、以及对不特定数据类型的支持 ,传入和返回类型一致
T表示泛型,具体什么类型是调用方法的时候决定的
function getData<T>(value:T):T{
return value;
}
getData<number>(123)
class MinCla<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;
var m2=new MinClas<string>(); //实例化类 并制定了类的T代表的类型是number;
- 泛型接口
interface ConfigFn{
<T>(value:T):T;
}
var getData:ConfigFn=function<T>(value:T):T{
return value;
}
getData<string>('zhangsan');
getData<string>(123); //错误
- 装饰器
装饰器是一个方法,可以注入到类、方法、属性参数上来扩展类、属性、方法、参数的功能。
常见的装饰器有:类装饰器、属性装饰器、方法装饰器、参数装饰器
- 类装饰器:在类声明前被声明(紧靠着类),可以用来监视修改或替换类。传入一个参数。
function logClass(params:any){
console.log(params) //params 就是当前类
params.prototype.apiUrl='aaaa';
params.prototype.run=function(){
console.log('我是一个run方法')
}
}
@logClass
class HttpClient{
constructor(){
}
getData(){
}
}
var http:any=new HttpClient();
console.log(http.apiUrl) // aaaa
http.run();
1.2 类装饰器:装饰器工厂(可传参)
function logClass(params:string){
return function(target:any){
console.log(target); // 当前类
console.log(params); //hello
target.prototype.apiUrl=params;
}
}
@logClass('hello')
class HttpClient{
constructor(){
}
getData(){
}
}
var http:any=new HttpClient();
console.log(http.apiUrl) // aaaa
1.3. 类装饰器,重载构造函数的例子
function logClass(target:any){
console.log(target);
return class extends target{
apiUrl:any='我是修改后的值';
getData(){
apiUrl=this.apiUrl+'111'
}
}
}
@logClass('hello')
class HttpClient{
constructor(){
}
getData(){
}
}
var http:any=new HttpClient();
console.log(http.apiUrl) // aaaa
http.run();
2.属性装饰器
属性装饰器表达式会在运行时当作函数被调用,传入下列2个参数
1.对于静态成员来说是类的构造函数,对于实例成员是类的原型对象。
2.成员的名字
function logClass(params:string){ //类装饰器
return function(target:any){
console.log(target); // 当前类
console.log(params); //hello
}
}
//属性装饰器
function logProperty(params:any){
return function(target:any,attr:any){
console.log(target);
console.log(attr);
target.attr=params;
}
}
@logClass('hello')
class HttpClient{
@logProperty('http:itying.com')
public url:any | undefined;
constructor(){
}
getData(){
console.log(this.url);
}
}
var http:any=new HttpClient();
console.log(http.apiUrl) // aaaa
http.run();
3.方法装饰器 - 会被应用到方法的属性描述符上,可以用来监视修改或者替换方法定义。
方法装饰器会在运行时传入下列三个参数
1.对于静态成员来说是类的构造函数,对于实例成员来说是类的原型对象。
2.成员的名字
3.成员的属性描述符。
function get(params:any){
return function(target:any,methodName:any,desc:any){
console.log(target); // 当前类
console.log(methodName) //getNData
console.log(desc.value) //getData方法
//修改装饰器的方法 把所有参数改成string类型
//保存当前方法
var oMethod=desc.value;
desc.value=function(...args:any[]){
args=args.map((value)=>{
return String(value)
})
oMethod.apply(this,args); //如果没这句,会覆盖getData方法。
}
}
}
class HttpClient{
public url:any | undefined
constructor(){
}
@get('http://dddd')
getData(...args:any[]){
console.log(this.url)
}
}
- 装饰器 的执行顺序:
属性 > 方法 > 方法参数 >类
如果有多个,则从后向前执行
网友评论