系列文章目录
提示:阅读本章之前,请先阅读目录
文章目录
前言
环境搭建
基本类型
// 1. 定义变量
let username: string = "xmf";
let age: number = 999;
let state: boolean = false;
// 2. 定义函数
function addNumber(one: number, two: number, str: string): string {
return one + two + str
}
// 3. 联合类型
let nickname: number | string;
// 4. 使用字面量作为类型限制,和常量一样,不能修改
let url: "localhost";
// 5. 字面量 + 联合类型,可以达到,作为选项的效果
let sex: "男" | "女";
// 6. any,任意类型
let test1: any;
test1 = 1;
test1 = "hhhhh";
test1 = true;
// 7. any 只要赋值给对方,对方也不会限制类型
let bossname: string;
bossname = test1; // 不会报错
// 8. unknown 未知类型的值,但是不能拿来赋值给其他变量
let unk: unknown;
unk = 8888;
bossname = unk; // 报错
// 9. 类型断言,告诉解析器,值的类型
bossname = <string>test1; // 写法1
bossname = test1 as string; // 写法2
// 10. void 无返回内容,但是可以返回null和undefined
function fun(): void {
return;
}
function fun(): void {
return null;
}
function fun(): void {
return undefined;
}
// 11. never 无返回内容,但是不可以返回任何内容,包括null和undefined
function fun1() {}
// 12. 对象
let obj1: {};
let obj2: object;
let obj3: { name: string, age: number };
obj3 = { name: "123" }; // 报错,因为没有传入age
obj3 = { name: "123", age: "123" } // 报错,因为age传入的是字符串类型
obj3 = { name: "123", age: 133, tel: 123 } // 报错,因为多传了参数
let obj4 = { name: string, age?: number }; // age是可选值,可传可不传
let obj5 = { name: string, [propName: string]: any } // 表示后面可传入任意的参数
obj5 = { name: "hhhh", age: 12, tel: 18, address: "hk"}; // 正确
let obj6: (a: string, b: string, c: number) => string; // 限制类型为函数,并规定传参和返回值类型
obj6 = function(n1: string, n2: string, n3: number): string {
return n1 + n2 + n3
}; // 正确
// 13. 数组类型
let arr1: string[]; // 字符串数组类型
let arr2: number[]; // 数字数组类型
let arr3: Array<string>; // 等于与字符串数组类型string[]
// 14. 元祖,固定长度
let arr4: [string, string];
arr4 = [1,2] // 正确
arr4 = [1,2,3,4] // 报错
// 15. 枚举enum
enum Student {
xiaoming = 1,
xiaohong = 2
}
let stu = { username: Student };
stu = { username: Student.xiaoming };
// 16. 同时满足 &
let obj7: { name: string } & { age: 18 }
// 17. 类型的别名
type usernameType = "xm" | "xmf" | "hhh";
let stu1: usernameType;
let stu2: usernameType;
let stu1: "xm" | "xmf" | "hhh"; // 等价于这个
编译选项
// 1. 在ts根目录,创建一个tsconfig.json文件
// include,代表包含此路径的ts文件,都会被编译
// ** 代表任意目录
// * 代表任意文件
{
"include": [
"./src/hello/**/*",
"./data/**/*"
]
}
// exclude,代表,包含此路径的文件,不会被编译
{
"exclude": [
"./src/test/**/*"
]
}
// 2. 执行命令 tsc
// 3. files,指定具体的ts文件,就会被编译
{
"files": [
"./src/hello/demo01.ts"
]
}
// 4. extends 继承某配置文件
{
"extends": "./config/test.json"
}
// 5. compilerOptions 配置项
{
compilerOptions: {
// 指定编译的ES版本
"target": "es6",
// 指定使用模块化的版本
"module": "es2015",
// 指定要使用哪些库,作为语法检查
"lib": ["dom"],
// 指定输出的文件夹
"outDir": "./dist",
// 指定输出一个文件
"outFile": "./dist/app.js",
// 是否对js文件,也进行编译
"allowJs": true,
// 是否进行js语法检查
"checkJs": true,
// 编译完,是否还显示注释
"removeComments": true,
// 不生成编译文件js
"noEmit": true,
// 编译报错,不生成编译文件
"noEmitOnError": true,
// 编译后的文件,是否开启严格模式
"alwaysStrict": true,
// 不允许隐式的any类型
"noImplicitAny": true,
// 不允许不明确的this
"noImplicitThis": true,
// 严格检查控制
"strictNullChecks": true,
// 所有严格的总开关
"strict": true
}
}
webpack
1. 初始化配置
npm init -y
2. 安装依赖
npm i -D webpack webpack-cli typescript ts-loader
3. 创建index.js
4. 创建tsconfig.json
5. 创建webpack.config.js
const path = require("path")
module.exports = {
// 指定入口文件
entry: "./src/index.ts",
// 指定打包所在目录
output: {
path: path.resolve(__dirname, "dist"),
filename: "bundle.js"
},
// 指定打包时,使用的模块
module: {
// 指定规则
rules: [
{
// 指定规则
test: /\.ts$/,
// 指定loader
use: "ts-loader",
// 排除文件
exclude: /node_modules/
}
]
}
}
6. 配置package.json
{
"name": "demo04",
"version": "1.0.0",
"description": "",
"main": "test.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1",
// 就是这行代码
"build": "webpack"
},
"keywords": [],
"author": "",
"license": "ISC",
"devDependencies": {
"ts-loader": "^9.4.2",
"typescript": "^4.9.5",
"webpack": "^5.76.1",
"webpack-cli": "^5.0.1"
}
}
7. npm run build
webpack 插件
// 1. html-webpack-plugin 自动生成html文件
// 安装 npm i -D html-webpack-plugin
// 配置 webpack.config.js
const HtmlWebpackPlugin = require("html-webpack-plugin")
plugins: [
new HtmlWebpackPlugin({ template: "./src/index.html" })
]
// 2. clean-webpack-plugin 自动清除每次编译生成的文件
// 安装 npm i -D clean-webpack-plugin
// 配置 webpack.config.js
const { CleanWebpackPlugin } = require("clean-webpack-plugin")
plugins: [
new CleanWebpackPlugin()
]
// 3. webpack-dev-server 编译完成后,自动打开浏览器,并且代码变动,自动重新编译
// 安装 npm i -D webpack-dev-server
// 配置package.json
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1",
"build": "webpack",
"start": "webpack serve"
}
// 配置 webpack.config.js
devServer: {
static: path.join(__dirname, './'), // 指定发布后的映射的路径,./代表映射当前路劲
compress: true, // 压缩资源
port: 9000, // 指定服务器的端口号
open: true, // 指定以哪个浏览器打开,open:true 代表以默认浏览器打开
}
// 4. 配置webpack,能够识别导入模块
// 比如在 ts文件里面,import xx from "test.js"
// 配置 webpack.config.js
resolve: {
extensions: ['.ts', '.js']
}
webpack的babel
// 1. 安装
npm i -D @babel/core @babel/preset-env babel-loader core-js
// 2. webpack.config.js整体配置
const path = require("path")
const HtmlWebpackPlugin = require("html-webpack-plugin")
const { CleanWebpackPlugin } = require("clean-webpack-plugin")
module.exports = {
// 设置打包模式
mode: "development",
// 指定入口文件
entry: "./src/index.ts",
// 指定打包所在目录
output: {
path: path.resolve(__dirname, "dist"),
filename: "bundle.js",
// 配置webpakc,打包环境
environment: {
// 不使用箭头函数
arrowFunction: false
}
},
// 指定打包时,使用的模块
module: {
// 指定规则
rules: [
{
// 指定规则
test: /\.ts$/,
// 指定loader, 最前面是最后执行
use: [
{
// 指定加载器
loader: "babel-loader",
// 设置babel
options: {
// 设置预定义环境
presets: [
[
// 指定环境插件
"@babel-preset-env",
// 配置信息
{
// 要兼容的目标浏览器
targets: {
"chrome": "88",
"ie": 11
},
// 指定corejs的版本
"corejs": "3",
// 指定加载方法,usage按需加载
"useBuiltIns": "usage"
}
]
]
}
},
"ts-loader"
],
// 排除文件
exclude: /node_modules/
}
]
},
// 引入插件
plugins: [
new HtmlWebpackPlugin({ template: "./src/index.html" }),
new CleanWebpackPlugin()
],
devServer: {
static: path.join(__dirname, './'), // 指定发布后的映射的路径,./代表映射当前路劲
compress: true, // 压缩资源
port: 9000, // 指定服务器的端口号
open: true, // 指定以哪个浏览器打开,open:true 代表以默认浏览器打开
},
resolve: {
extensions: ['.ts', '.js']
}
}
class类
class Person {
// 静态属性
static name: string = "xmf";
// 静态方法
static sayHello() {
return 1;
}
// 只读属性,不可修改
readonly age: number = 18;
// 静态+只读,静态必须写在最前面
static readonly money: number = 999999;
// 普通属性
address: string = "1231213";
}
const p = new Person();
p.name;
p.sayHello();
constructor 构造函数
class Dog {
name: string;
age: number;
constructor(name: string, age: number) {
this.name = name
this.age = age
}
}
const d = new Dog({ name: "hhh", age: 888})
class类的继承 extends
class Animal {
name: string = "animal";
age: number = 999;
constructor(name: string, age: number) {
this.name = name
this.age = age
}
sayHello() {
console.log("I am is animal");
};
}
// extends继承
class Dog extends Animal {
run() {
console.log("Dog is run")
}
}
class Cat extends Animal {
// 重写
sayHello() {
console.log("I am is cat")
}
}
class的super
class Animal {
name: string = "animal";
age: number = 999;
constructor(name: string, age: number) {
this.name = name
this.age = age
}
sayHello() {
console.log("I am is animal");
};
}
// extends继承
class Dog extends Animal {
name: string = "dog";
age: number = 888;
// 子类重写父类的构造函数,那么,必须调用super()
constructor(name: string, age: number) {
super(name, age);
this.name = name;
this.age = age;
}
run() {
// super就是父类的实例,所以可以直接掉父类的方法
super.sayHello();
}
}
class 抽象类 abstract
// 抽象类,无法被实例化,只能被继承
abstract class Animal {
name: string = "animal";
age: number = 999;
constructor(name: string, age: number) {
this.name = name
this.age = age
}
// 抽象方法,子类必须重写
abstract sayHello(): void;
}
// extends继承
class Dog extends Animal {
// 必须重写父类的抽象方法
sayHello() {
console.log("Dog is run")
}
}
class的接口interface
// 接口是可以重复定义的
interface myInterface {
name: string;
age: number;
sayHello(): void;
};
interface myInterface {
address: string
};
// 实现接口
class Dog implements myInterface {
name: string;
age: number;
address: string;
constructor(name: string, age: number, address: string) {
this.name = name
this.age = age
this.address = address
}
sayHello() {
console.log("2222")
}
}
属性的封装
class Student {
// 公开属性
public schoolName: string;
// 私有属性
private _name: string;
private _age: number;
// 半公开,子类也可以获取
protected phone: string;
constructor(name: sting, age: number) {
this._name= name;
this._age = age;
}
// get方法,调用的时,直接student.name
get name() {
return this._name
}
set name(val: string) {
this._name = val
}
}
class xiaoming {
constructor() {
this.super()
}
getPhone() {
console.log("我可以拿到父类", this.phone)
}
}
泛型
function test<HELLO>(name: HELLO): HELLO {
reutrn name;
}
test<string>("xmf");
test<number>(999);
class Student<T> {
name: T;
constructor(name: T) {
this.name = name;
}
}
function test2<T, K>(name: T, age: K): T {
return name;
}
interface InterName {
name: string;
age: number;
}
function test3<K extends InterName>(name: K): K {}