实习一个月了,由于公司是做管理系统的,暂不涉及高并发、分布式之类的后台问题,好吧,主要是增删改查,前后台都得写,主要是要学习前端框架,之前完全没涉及过。目前angular还在进行中,可供学习和参考的资料很少,除了官网比较详细,其他的基本也是参看的官网的例子,我按照我的学习,还是整几篇博客,不想涉及概念之类的东西,发现自己写了一百多篇文章,那种通篇大论的自己都懒得去翻看。
学习typescript的时候做了一些笔记,就在angular之前放一篇typescript的笔记吧!
开发工具:首选VS code。 node、npm或者cnpm这些环境问题不在此重复!
目录
一、ts编译成js的命令
typescript编译成JavaScript:在终端(在要编译的文件所在目录下)使用命令 tsc xxx.ts;
(http://www.typescriptlang.org/play/index.html 是typescript官网给出的在线编译器)
使用上述方法编译的话,所有ts文件和编译后得到的js文件都混在一起,
使用命令 tsc --outDir dist helloworld.ts 会把编译后的js文件放在dist文件下;
使用命令 tsc --outDir dist ./src/helloworld.ts 在上面的基础上,把ts文件放在了src文件下,src与dist平级。
上述方式编译还有一个问题就是:每修改一下代码或者新增一个ts文件都需要编译一次,下面是解决方案:
使用 tsc --init 命令创建一个tsconfig.json文件;
打开 tsconfig.json 文件,取消 "outDir": "./", "rootDir": "./", 两行的注释;
修改为:"outDir": "./dist", "rootDir": "./src", 这样敲一下tsc以后就帮我们编译了。
到这里,还没完喔!!!因为文件有变动还是要敲一下tsc,所以我们需要设置自动监测:tsc -w,w表示watch。
注:单独只敲tsc是编译该目录下所有文件。
二、typescript的数据类型
typescript定义变量需要制定类型!!!``是反单引号,ES6中的内容,在此不多说!
1.布尔类型(boolean)
// boolean 只能是true/false
let flag: boolean = false;
console.log(`flag = ${flag}`); //flag = false
// 给flag赋别的类型的值(1、0都不行),在vc code中会提示有错误,当然也是不能通过编译的!
2.数字类型(number)
//number除了支持十进制和十六进制字面量,TypeScript还支持ECMAScript 2015中引入的二进制和八进制字面量。
let n1:number = 10; //十进制
let n2:number = 0o744; //八进制
let n3:number = 0b1011; //二进制
let n4:number = 0x1f; //十六进制
console.log(`八进制0o744=${n2} 二进制0b1011=${n3} 十六进制0x1f=${n4}`); //八进制0o744=484 二进制0b1011=11 十六进制0x1f=31
3.字符串类型(string)
let str1: string = "hahaha 我是字符串"; //hahaha 我是字符串
let str2: string = `我是模板字符串,内含变量 ${10}`; //我是模板字符串,内含变量 10
console.log(str1);
console.log(str2);
4.数组类型(array)
let arr1: number[] = [1,3,5,7]; //number类型的数组,只能放number
// let arr: Array<number> = [1, 2]; //数组泛型,这也是一种定义数组的方式
console.log(arr1); //[ 1, 3, 5, 7 ]
arr1[6] = 13;
console.log(arr1); //[ 1, 3, 5, 7, <2 empty items>, 13 ]
console.log(arr1[5]); //undefined
console.log(arr1[9]); //undefined
// string类型的数组,只能存放字符串,可以是"" 、'' 、`` 三种引号引起来的字符串
let arr2: string[] = ['hello', "javascript", "typescript", `hi`]; //[ 'hello', 'javascript', 'typescript', 'hi' ]
console.log(arr2);
let arr3: any[] = [1, "any-type", {"score": 80}]; //[ 1, 'any-type', { score: 80 } ]
console.log(arr3);
// 多维数组
let arr4: number[][] = [
[1,2,3,4,5],
[6,7,8,9,10],
];
console.log(arr4[0]); // 第一行 // [1,2,3,4,5]
console.log(arr4);
5.元组类型(tuple)
// 元祖类型用来表示已知元素数量和类型的数组,每个元素的类型不必相同。
let tup: [number, number, string, boolean] = [20, 12.3, "tuple-type", true];
console.log(tup); //[ 20, 12.3, 'tuple-type', true ]
6.枚举类型(enum)
// 枚举是一个可被命名的整型常数的集合,枚举类型为集合成员赋予有意义的名称,增强可读性
enum Log {all, debuger, info}; // 定义枚举
let l:Log = Log.debuger; // 变量赋值
console.log('log = ', l); // 如果没有定义值,就是从下标开始,这里返回下标1。 log = 1
enum Log2 {'all' = '全部', debuger = '调试', info = '部分'};
let l2:Log2 = Log2.all;
console.log('log = ', l2); // 如果有定义的值,返回定义的值。 log = 全部
7.任意值类型(any)
// 任意类型。不推荐使用
let anyInfo:any = 'abc'
anyInfo = 12334;
console.log('any = ', anyInfo); //any = 12334
8.null 和 undefined
// undefined
let u1:undefined;
console.log('u1 = ',u1); //u1 = undefined
let u2:number | undefined;
console.log('u2 = ', u2); //u2 = undefined
// null
let var1:null = null;
console.log('var1 = ', var1); //var1 = null
let var2:string | null | undefined;
var2 = 'abc'
console.log('var2 = ', var2); //var2 = abc
//空检查(不允许变量有null值)
// 将tsconfig.json文件中的 "strictNullChecks": true 取消注释,在终端中敲tsc命令编译,
// 有变量是空值(null)的话就会报错,不会通过编译。
9.void 类型
let voidFun1 = ():void => { console.log("这个箭头函数没有返回值!"); }
let fun2 = ():number => { return 123; }
let fun3 = ():any => { return "hi"; }
console.log(`fun2 = ${fun2} fun3 = ${fun3}`);
//fun2 = function () { return 123; } fun3 = function () { return "hi"; }
10.never 类型
// never类型表示的是那些永不存在的值的类型
// 不能将其他类型分配给类型“never”, 比如 let a:never = 123; 是不可行的
let a:never;
a = (()=>{
throw new Error('出错了!!!')
} )()
console.log('a = ', a);
/**
throw new Error('出错了!!!');
^
Error: 出错了!!!
at D:\code\angular\ts-test\src\variableType.js:92:11
at Object.<anonymous> (D:\code\angular\ts-test\src\variableType.js:93:3)
at Module._compile (internal/modules/cjs/loader.js:701:30)
at Object.Module._extensions..js (internal/modules/cjs/loader.js:712:10)
at Module.load (internal/modules/cjs/loader.js:600:32)
at tryModuleLoad (internal/modules/cjs/loader.js:539:12)
at Function.Module._load (internal/modules/cjs/loader.js:531:3)
at Function.Module.runMain (internal/modules/cjs/loader.js:754:12)
at startup (internal/bootstrap/node.js:283:19)
at bootstrapNodeJSCore (internal/bootstrap/node.js:622:3)
*/
三、typescript中的面向对象
1、ts中属性和方法的修饰符
默认修饰符是public。各个修饰符的权限和Java一样,不过ts没有default修饰符,只有以下三种:
* public 公有的 类内、类外都可以访问
* protected 受保护的 只能在本类内和子类中才可以访问
* private 私有的 只能在本类中访问
另外ts中也有 static关键字,它可以修饰属性、方法。静态属性和方法可以直接通过类名访问,不用实例化。
2、继承
// 用 class 关键字 定义一个类
class Person {
public name: string;
constructor(name: string) {
this.name = name;
}
getName() : string {
return this.name;
}
setName(name:string) {
this.name = name;
}
beat() : string {
return `${this.name}的心脏在跳动`;
}
}
var p = new Person('张三');
console.log(p.getName()); //张三
// 用 extends 关键字表示继承关系
class Men extends Person {
constructor(name : string) {
super(name); //初始化父类的构造函数
}
}
var man = new Men("小马");
console.log(man.beat()); //小马的心脏在跳动
3、接口
// 属性接口
// ts中自定义方法传入参数,对json进行约束
interface FullName{
firstName:string;
lastName:string;
}
function printName(name: FullName) {
console.log(name.firstName + "---" + name.lastName);
}
var obj={ //传入的参数必须包含 firstName 和 lastName
age: 20,
firstName: 'Smith',
lastName: 'Johnson'
};
printName(obj);
下面定义的Config接口中data属性是可选的,即可有可无
//接口 可选属性 ?
interface Config{
type: string;
url: string;
data?: string;
dataType: string;
}
function ajax(config: Config) {
var xhr = new XMLHttpRequest();
xhr.open(config.url, 'true');
xhr.send(config.data);
xhr.onreadystatechange = function() {
if(xhr.readyState == 4 && xhr.status == 200) {
console.log("success");
if(config.dataType == 'json') {
JSON.parse(xhr.responseText);
} else {
console.log(xhr.responseText);
}
}
}
}
ajax({
type: 'get',
url: 'http://www.baidu.com', //这里应该是api接口,这里使用这个url是不行的,以实际为准,这里只是举例。
dataType: 'json'
})
函数类型接口
//函数类型接口
interface encrypt {
(key:string, value:string) : string;
}
var md5: encrypt = function(key:string, value:string) : string {
return key+value;
}
console.log(md5("name","zhangsan"));
类类型接口
// 类类型接口(对类的约束 和抽象类类似)
interface Animal {
name : string;
eat(food : string) : void;
}
class Cat implements Animal {
name : string;
constructor(name: string) {
this.name = name;
}
eat(food: string) {
console.log(`Cat ${this.name} 吃 ${food} 猫粮`);
}
}
// Person2接口继承Animal接口
interface Person2 extends Animal {
work(time: string) : void ;
}
// Adult类实现Person2接口, 不仅要实现Person2接口中的方法和属性,还要实现Animal接口中的方法和属性
class Adult implements Person2 {
name : string;
constructor(name: string) {
this.name = name;
}
eat(food: string) : void {
console.log(`工作很忙,吃点${food}就好`);
}
work(time: string) {
console.log(`每天${time}点开始工作`);
}
}
4、泛型
泛型函数
// 泛型函数 可以支持不特定的数据类型 传入的参数类型和返回的数据类型一致。
function getData1<T>(value : T): T {
return value;
}
getData1<string>("123abd"); //只能传入string类型的参数{(返回参数只能是string类型))
getData1<number>(123); //只能传入number类型的参数(返回参数也只能是number类型)
泛型类
// 泛型类
class MinClass<T> {
public list: T[] = [];
add(value : T) {
this.list.push(value);
}
min():T {
var minNum = this.list[0];
for(var i=1; i<this.list.length; i++) {
if(minNum>this.list[i]) {
minNum = this.list[i];
}
}
return minNum;
}
}
var m1 = new MinClass<number>(); //实例化类 并制定了T的具体类型
m1.add(10);
m1.add(2);
m1.add(24);
console.log(m1.min());
泛型接口
// 泛型接口 方式一:
interface ConfigFn1{
<T>(value:T):T;
}
var getData2:ConfigFn1 = function<T>(value:T):T {
return value;
}
console.log(getData2<string>("李四"));
// 泛型接口 方式二:
interface ConfigFn2<T> {
(value:T):T;
}
function getData3<T>(value: T):T {
return value;
}
var mygetData:ConfigFn2<string> = getData3;
console.log(mygetData("小明"));