智能合约开发——TypeScript 基础(全)

TS 准备

首先我们准备一个目录,使用 dos 进入到某目录,当然你直接 vs 打开终端执行也是没有问题的:
在这里插入图片描述
执行以下命令安装 typescrip(不用进入目录,直接安装即可):

npm install -g typescript

我是已经安装过了:

在这里插入图片描述
接着你可以初始化项目(这里需要进入文件夹了,毕竟是你的项目目录对吧,初始化项目就是以当前目录默认初始化):

tsc --init

在这里插入图片描述
此时你的目录中会出现一个 tsconfig 文件:
在这里插入图片描述

里面存储的是一些 ts 的config ,暂时不用理,接下来就可以开始 ts 的编程了。

一、TS 编译

安装好 nodejs 之后,新建一个 01.ts 文件:
在这里插入图片描述
编写代码:

console.log("HI") 

由于 ts 最终将会编译生成 js,你在 ts 中直接写 js 是没有问题的(并且ts不是一个全新的语言,是基于 js 的),在终端中输入 node 01.ts:

在这里插入图片描述

此时将会输出 HI~。

二、变量定义及编译

在 ts 变量定中需要指定的这个变量类型,这个是跟 js 大有不同,又或者说这该指定类型贯穿了整个 ts。

更改 01 代码:

let age: number = 18;
console.log(age)

以上代码中定义了一个 age变量,类型为 number,赋值为 18,此时在变量名之后有一个冒号,冒号右侧就是对应的这个变量的类型,最终使用等于号赋值为 18。

此时由于我们私用的是 ts 的语法,你直接使用 node 话会错误,需要使用 tsc-node 命令对 ts 文件进行编译:

在这里插入图片描述
若你使用 node 命令就不是编译了,此时将会报错:
在这里插入图片描述
使用 node 表示运行 js 文件,而不是 编译 ts 文件。

在创建一个变量的时候,也可以不指定类型,直接给定一个值,这个时候 ts 会完成类型的自动推导(跟go类似),这样就知道这个变量是什么值了,例如:

let age = 11;

三、生成 js 文件

在 ts 中,还可以直接使用 tsc 对 ts 编译生成 js 文件:
在这里插入图片描述
执行命令后,将会在当前目录下生成一个 js 文件,并且这个 js 文件是对应 ts 的 js 代码:
在这里插入图片描述
在这里插入图片描述
在此我们一定要注意, ts 你可以理解为是一种强制性的“规范语法”框架,在该“语法框架”下需要严谨的对某些动作进行处理,但最终的本质还是 js。

四、变量、数组

4.1 一般数据类型

ts 中类型有 number、string、boolean、symbol、数组、map 等,在此只介绍常见类型。

以下是对应这些类型的示例:

let age: number = 18;
let authorName: string = '1_bit';
let boolVal: boolean = true;//数组
let strs: string[] = ["1_bit", "blog", "author"];
let strOrNumber: (string | number)[] = ["1_bit", 11, "blog", "author", 22];

以上的示例中,主要看数组的定义,例如 let strs: string[] = ["1_bit", "blog", "author"];,在这段代码中 strs 是数组名,冒号后就是对应的类型约束,在此是 string,而方括号 “ [] ” 则表示这是一个数组,在等于号右侧则是这个数组中的值。

已经理解了基本的数组的 ts 数组,在查看对应的 strOrNumber 数组,在这个代码中,用圆括号包裹了 string 和 number 并且中间使用了“或”运算的 “ | ” 链接,这是表示这个数组中可以存储 string 以及 number 类型,所以在数组中可以看到 string 和 number 类型的数据都存在。

4.2 元组

学过 python 的小伙伴对元组应该很熟悉,在 ts 中的元组跟 python 中的不是很一样,在 ts 中定义的元组你可以理解为固长、固定类型的数组,可以指定某个位置的类型以及指定整个数组的长度,以下为元组示例:

let postion: [number, number];
postion = [0.45, 0.50];console.log(postion)
console.log(postion[0])

以上代码中 let postion: [number, number]; 为定义了一个元组,但是并没有进行初始化,接下来直接给 postion 定义了一个值[0.45, 0.50],随后使用 console.log 对其打印。

在此我们可以看到,数组的定义方式是之直接在变量的冒号后面使用一个类型加方括号“[]”定义一个数组,在元组中则是在方括号内编写对应的数值类型。

运行后结果如下:
在这里插入图片描述

4.3 any

在 ts 中不推荐使用 any 类型,你用了不就等于跟原本的 js 没啥区别了吗?若真的有必要使用 any 推荐临时使用,别贯穿项目。

以下是any 的错误示范(语法正确,使用错误):

let age: any;
age = "str";
console.log(age)
console.log(typeof age)

结果如下:
在这里插入图片描述

五、自定义类型(别名)

在 ts 中,若一个数组的类型经常使用,可以定义一个类型别名,在使用这个类型时即可简短的通过这个别名表示这个类型:

type StuT = (string | number)[]
let stus: StuT = ["1_bit", 13, "Xi", 26]

以上示例定义了一个 type 类型,这个类型为 (string | number)[] 表示是一个字符串与数组的数组类型,接着在下一行代码中直接创建了一个 stus 变量,指定为 StuT 类型,并且赋值有字符串和数字的值。

六、函数

6.1 基本函数

ts 语言中的自定义函数跟 go 中的有点相似,例如如下是一个 ts 中的自定义函数:

function sayHi(name: string, age: number): string {return "Hi " + name + " you " + age + " age";
}
let xiName: string = "Xi";
let xiAge: number = 19;
console.log(sayHi(xiName, xiAge));

在以上示例中 sayHi 是一个自定义函数,跟js 语法一样,使用function 定义一个函数,在 sayHi 函数中有两个参数,一个是 name 还有一个是 age,name 参数是一个 string 类型,age 是一个 number 类型,参数的声明在此也是不同的,使用了 ts 的语法;还有一点不同的是在参数之后使用一个冒号说明了当前函数的返回值为一个 string,在此需要注意,这是 ts 的语法。

接着我创建了两个边路 xiName 以及 xiAge,用此当做参数传入到 sayHi 之中,此时使用 ts-node 命令编译运行我们的 ts 文件:
在这里插入图片描述

6.2 箭头函数

函数的编写还有另外一种使用箭头函数的方式:

const sayHi = (name: string, age: number): string => {return "Hi " + name + " you " + age + " age";
}
let xiName: string = "Xi";
let xiAge: number = 19;
console.log(sayHi(xiName, xiAge));

6.3 箭头函数加强版

函数还有另外一种定义方式,可能大家都不是特别想去学习:

const sayHi: (name: string, age: number) => string = (name, age) => {return "Hi " + name + " you " + age + " age";
}

其实这个形式可以看成两个部分:
在这里插入图片描述
其中前半部分是为这个 sayHi 声明一个类型,这个 sayHi 的类型是 (name: string, age: number) 由于需要指定这个函数返回值,所以使用 => string 表示当前函数返回值为 string。

接着我们再看第二个部分:
在这里插入图片描述
这一部分就直接当做函数的内容即可,而 (name, age) 表示这个函数接收两个参数,把之前所说明的 name 和 age 两个变量传入到函数,所以在此处并不用使用类型对其进行约束,在之前已经做好约束了,最后箭头函数右侧则是函数体。

函数返回值若为空则使用 void。

6.4 可选参数

可选参数在 ts 中表示这个参数可传或不传,非必须参数,例如我们现在修改以上示例完成需求“姓名必传、年龄和身高为可选,传入年龄或身高需要对应的对其进行显示”。

若完成这个需求那么必然会有一个函数对某个值进行判断,此时做一个检测的函数:

function isUndefine(arg: (number | string | undefined)): boolean {let check: boolean = true;if (!arg) {check = false;}return check;
}

以上检测 agr 参数,参数因为需要时 number、string、undefined 类型的其中一个,所以在此处设定了这个参数的类型范围,接着有一个 Boolean 的返回值,在函数体中给了一个变量 check 为 Boolean,初始值为 true,只要 arg 不存在那么久 fase 即可,最后返回 check。

接着我们修改 sayHi 函数,修改后调用检测参数的函数,完成内容的拼接:

const sayHi: (name: string, age?: number, height?: number) => string = (name, age, height) => {let sayStr = 'Hi ' + name;if (isUndefine(age)) {sayStr += " you " + age + " age";}if (isUndefine(height)) {sayStr += " you " + age + " age " + "height " + height;}return sayStr;
}

此时两个 if 判断 age 或者 height 是否存在,随后进行拼接即可,最后返回了sayStr 这个字符串。

在这里我们可以看到,参数 age、height 在参数名后添加了一个问号,这个问号就是表示可选参数。

最终完整代码如下:

function isUndefine(arg: (number | string | undefined)): boolean {let check: boolean = true;if (!arg) {check = false;}return check;
}const sayHi: (name: string, age?: number, height?: number) => string = (name, age, height) => {let sayStr = 'Hi ' + name;if (isUndefine(age)) {sayStr += " you " + age + " age";}if (isUndefine(height)) {sayStr += " you " + age + " age " + "height " + height;}return sayStr;
}
let xiName: string = "Xi";
let xiAge: number = 19;
console.log(sayHi(xiName, xiAge, 170));

最终传入不同的参数将会显示不同的结果:

在这里插入图片描述

七、对象

在 ts 中使用对象分为声明和定义,声明就像类型一样进行使用,定义则是赋予这个对象的值:

let stu: {name: string;age: number;height: number;getName(): string;getAge(): number;setName(name: string): void;setAge(age: number): void;} = {name: 'Xi',age: 11,height: 170,setName(name) {this.name = name;},setAge(age) {this.age},getName() {return this.name;},getAge() {return this.age},
}stu.setName("1_bit")
console.log(stu.getName())

以上实例中定义了一个 stu 的对象,其中包含 name、age、height 变量以及 getName 等方法,这些都可以看做是这个对象的“类型”,随后赋值为这些“类型”的初始化,并且设定函数的实现。

在此一定要注意,你既然声明了,那就必须要实现(若删除一个成员变量的初始化),否则会报错:
在这里插入图片描述
运行结果如下:
在这里插入图片描述

八、类

8.1 类的基本使用

在 ts 中定义一个类方式很简单,使用 class 例如如下示例:

class Stu {public readonly name: string;public age: number;private nickname: string = '';private readonly color = 'yellow';constructor(_name: string, _age: number) {this.name = _name;this.age = _age;}public setNickName(_nick: string) {this.nickname = _nick;}public getNickName() {return this.nickname;}
}

以上示例中使用 class 创建了一个 stu 类,在这个类中定义了几个成员变量,在这几个成员变量中使用了 public、private 对其进行修饰,public 表公开都可以调用,private 私有,自由类内部可以调用,除了这些常规的修饰之外还有一个 readonly,readonly 表示当前字段不允许修改,若你想对其进行改动那么将会报错:
在这里插入图片描述
在此还需要注意,这些变量你都需要对其进行初始化,否则将会报错。

在类中还有一个构造方法,ts 是支持构造方法的;在使用成员变量时需要使用 this 对其指向,直接使用变量名将会出错。

ts冷笑话:在 class 中创建“函数”不需要使用 function,因为他是方法。

接着创建一个对象:

const XiaoMing = new Stu("XiaoMing", 18);
XiaoMing.setNickName("MM");
console.log(XiaoMing.getNickName());

接着使用 tc 命令编译运行:

在这里插入图片描述

在 ts 中类的继承使用 extends:

class Stu1 extends Stu {public getName(): string {return this.name}
}

继承后在 Stu1将会拥有 Stu 的成员变量和方法,使用和正常一个对象使用一致:

const XiaoMing1 = new Stu1("XiaoM", 18);
console.log(XiaoMing1.getName());

8.2 函数重载

8.3 类的兼容性

以下是一个示例,在 ts 中相同成员变量的类可以互相兼容:

class Stu1 {name: string;height: number;constructor() {this.name = "xiaoM";this.height = 170;}
}class Stu2 {name: string;height: number;constructor() {this.name = "xiaoY";this.height = 160;}
}const xiaoY: Stu1 = new Stu2()

若此时 Stu2 中多了一个成员变量呢:
在这里插入图片描述

此时 Stu1 还是兼容于 Stu2 的,少的可以兼容于多的,若反过来是不可以的:
在这里插入图片描述
当然多个方法也没问题:
在这里插入图片描述

九、接口

9.1 接口的一般使用

在 ts 中支持接口,使用关键字 interface:

interface stuI {height: number;name: string;getName(): string;
}

以上定义了一个接口,若需要某些变量为该接口类型,那么就需要对接口中的变量进行初始化和实现方法:

let stu: stuI = {height: 170,name: "1_bit",getName() {return this.name;}
}

实现方法很简单,就是 let 一个变量后指定接口为类型,随后使用花括号对其中的内容进行初始化。

接口还可以继承,例如如下示例:

interface stuI1 extends stuI {color: string,getHeight(): number
}

以上 stuI1 继承 stuI,并且继承了其中的内容,在 stuI1 接口中可以为接口本身编写 stuI1 的内容。

使用也如下使用示例(需要完全实现接口、父接口的中的内容):

let stu1: stuI1 = {height: 170,name: "1_bit",color: "yello",getName() {return this.name;},getHeight() {return this.height}
}

最后调用:

console.log(stu.getName());
console.log(stu1.getHeight());

在这里插入图片描述

9.2 交叉类型与同名成员变量

交叉类型其实就是多个接口进行合并,如下示例:

interface BBB { name: string }
interface CCC { age: number }
interface DDD { height: number }type BCD = BBB & CCC & DDD
let val: BCD = {name: 'ccc',age: 123,height: 12121
}

交叉类型直接使用 & 对某个类型进行定义即可,之后的变量在使用这个类型的时候就必须实现这些接口中的内容。

若接口中有同名,那么那么变量就是 never 类型,表示不可能,永远不可能。

9.2 交叉类型与同名函数参数

在同名函数中的参数同名但类型不同的情况下可以理解为同时兼容于两个类型,例如:

interface CCC {age: number;getVl(key: number): string
}
interface DDD {height: number;getVl(key: string): string
}

以上两个接口新增了一个同名方法 getVl,参数同名却参数类型不同,此时就可以当成是 getVl(key: (number | string)),例如如下代码:

type BCD = BBB & CCC & DDD
let val: BCD = {name: 'ccc',age: 123,height: 12121,getVl(key: (number | string)) {console.log(key)return "1";}
}val.getVl(233);

十、泛型 后面有时间再补

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/285823.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

查看MySQL的当前日期

select current_date(); 查看MySQL的当前日期转载于:https://www.cnblogs.com/dengyg200891/p/5972698.html

【ArcGIS风暴】ArcGIS支持的栅格数据格式大全及格式转换案例精解

ArcGIS功能异常强大,支持多种常见的栅格数据格式,并可实现多个栅格格式的自由转换。 在ArcGIS中,常见的栅格数据格式有:TIFF、BMP、ENVI、Esri BIL、Esri BIP、Esri BSQ、GIF、GRID、IMAGINE Image、JP2、JPG、和PNG。 BIL —Esri 波段按行交叉格式文件BIP —Esri 波段按像…

Android之靠谱的获取本地相册图片

1、需要申请手机读写的权限 AndroidMani.xml里面配置权限 <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /><uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" /> 我们一般采用RxPe…

利用Signalr实现手机端App扫码登录web页面

实现原理&#xff1a; 1、web登录页面&#xff0c;利用jquery.qrcode展示一个随机生成的登录码的二维码&#xff1b; 2、手机App扫描二维码取得登录码&#xff1b; 3、手机App将本地用户id登录码通过api提交服务器&#xff1b; 4、服务器api&#xff0c;收到手机App请求&am…

【ArcGIS风暴】ArcGIS栅格影像(NDVI)归一化处理的两种方法精解

【ArcGIS遇上Python】ArcGIS批量处理栅格影像(NDVI)归一化完整案例代码 图像归一化是指对图像进行了一系列标准的处理变换,使之变换为一固定标准形式的过程,该标准图像称作归一化图像。 原始图像在经历一些处理或攻击后可以得到多种副本图像,这些图像在经过相同参数的图像…

[从C到C++] 1.3 C++布尔类型(bool)

布尔类型(bool)是C新增的一种基本数据类型。在标准的C语言中并未定义bool类型&#xff0c;如果需要使用bool类型&#xff0c;程序员可以通过宏定义来自定义一个bool类型&#xff0c;定义语句如下&#xff1a; #define bool int #define false 0 #define true 1 也就是将int型定…

以小见大:一个领域建模的简单示例,理解“领域驱动”。

背景&#xff1a;航空公司为了确保飞行路线不发生冲突&#xff0c;需要开发一款飞行路线管理软件。过程&#xff1a;我们先去找这个领域的专家&#xff0c;自然是作为平时管理和维护机场飞行秩序的工作人员&#xff1b;我们第一个目标就是与他们沟通&#xff0c;也许我们并不能…

hibernate -- hello world

http://developer.51cto.com/art/201202/315931_all.htm转载于:https://www.cnblogs.com/iOS-mt/p/5973646.html

Android之底部Dialog里面放EditText点击布局顶上去效果

1、需求 在底部Dialog里面放EditText点击,布局需要顶上去,不顶上去很烦。 2、Dialog里面关键样式属性 <item name="android:windowFullscreen">false</item> 3、布局代码简单试下 样式 <style name="DialogTheme" tools:ignore="…

SignalR ——Android实践

SignalR 的版本&#xff1a;aspnetcore-2.2, Java SignalR-1.0.0 一、先说几个点 1、我使用SignalR的时候服务器使用的是自签名的HTTPS证书&#xff0c;所以OkHttp是无法直接解析的&#xff0c;会报错。需要修改SignalR里面OkHttp部分的源码&#xff0c;让其信任所有的HTTPS连…

【ArcGIS遇上Python】ArcGIS批量处理栅格影像(NDVI)归一化完整案例代码

文章《ArcGIS栅格影像(NDVI)归一化处理的两种方法精解》详细介绍了ArcGIS中进行NDVI影像归一化处理的两种方法,但是无法批量进行,本文就放大招用Python实现批量NDVI归一化处理,大大提高了工作效率,还不赶快Get了? 完整Python代码: import arcpy from arcpy import env…

Spark1.0.0 属性配置

1&#xff1a;Spark1.0.0属性配置方式Spark属性提供了大部分应用程序的控制项&#xff0c;而且能够单独为每一个应用程序进行配置。在Spark1.0.0提供了3种方式的属性配置&#xff1a;SparkConf方式 SparkConf方式能够直接将属性值传递到SparkContext&#xff1b;SparkConf能够对…

Lync Server 2010迁移至Lync Server 2013部署系列 Part1: 扩展AD架构

由于最近直在忙Lync 升级&#xff0c;好久没有更新博客了&#xff0c;今天开始将对最近做的Lync Server 2010迁移至Lync Server 2013项目做一个系列的部署操作更新&#xff0c;希望能给即将在企业中部署的兄弟们有所帮助&#xff0c;在这个测试环境中&#xff0c;企业 前端池共…

Android之BaseRecyclerViewAdpater(3.0.4版本)当页面第二次滑到底部的时候没有触发OnLoadMoreListener监听的onLoadMore函数

1 、问题 BaseRecyclerViewAdpater(3.0.4版本)当页面第二次滑到底部的时候没有触发OnLoadMoreListener监听的onLoadMore函数,也就是梅如下监听的地方 adapter?.loadMoreModule?.setOnLoadMoreListener(object : OnLoadMoreListener {override fun onLoadMore() {Log.d(TAG,…

Hello Playwright:(7)模拟键盘和鼠标

尽管在上一节中&#xff0c;我们已经能够通过FillAsync或ClickAsync来实现输入和点击元素。但是&#xff0c;还有其他场景&#xff0c;我们必须模拟用户使用键盘、鼠标与页面交互。例如在线文档&#xff1a;Page.Keyboard 对象Keyboard提供用于管理虚拟键盘的 API&#xff0c;它…

精通Hibernate:通过Hibernate操纵对象

http://developer.51cto.com/art/201202/315954.htm转载于:https://www.cnblogs.com/iOS-mt/p/5973683.html

【ArcGIS遇上Python】Python批量将多个文件夹下的多个影像数据镶嵌至新栅格

ArcGIS虽然可以实现一次多个影像同时参与,拼接成一个整的影像,但是通常情况下,多个影像并不在同一个文件夹下,这样拼接的时候需要逐个手动进行添加,如果数据量大的话,跟不就不可取,针对这一问题,本文采用Python,实现将多个文件夹下的多个影像拼接,高效快速。 我们以…

2019全球开发者调查:仅2%的人996,Python并不是最受喜爱的语言

导读&#xff1a;开发者社区正在发生哪些变化&#xff1f;Stack Overflow 的最新调查获得了一些预料之外的结果&#xff1a;Java 语言开发者的平均收入不到 35 万元人民币&#xff0c;成为了收入最低的群体&#xff1b;另一方面&#xff0c;人工智能领域流行的 Python 并不是最…

Java 编写程序 创建一个游戏【5、6两章的内容】【第5章】

每次使用单边大脑的时间不要太久&#xff0c; 连续使用左边脑30 分钟如同使用左臂 30 分钟一样&#xff0c; 周期性性地交换让大脑两侧轮流休息。 左脑活动包括了循序渐进的工作&#xff0c;解决逻辑问题与分析&#xff1b; 右脑的活动包括了阴雨、创造性思考、模式匹配与可视化…

一般地

2019独角兽企业重金招聘Python工程师标准>>> 1.EO的Updatable属性默认为Always&#xff0c;基于EO创建的VO也是。而基于SQL创建VO的Updatable属性默认为Never&#xff0c;如果要修改&#xff08;例如将VO拖至页面生成Form用于新增&#xff09;&#xff0c;则需将该属…