版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/aqtata/article/details/82586702
一、枚举类型
type
Day = enum
Monday, Tuesday, Wednesday
var d = Monday
echo d # Monday
d = Day(1)
echo d # Tuesday
和其他语言一样,枚举类型第一个元素值默认从0开始,逐渐+1,但也可以自己指定值
type
Day = enum
Monday = 5, Tuesday, Wednesday = 10
var d = Monday
echo ord(d) # 5
d = Tuesday
echo ord(d) # 6
二、有序类型
有序类型不是值一个具体的类型,是泛指内存中用数字存储的类型,比如int、bool、char、enum
var b = false
# ord方法得到对应的整数值
echo ord(b)
# inc方法将值+1
inc(b)
echo b # true
# 超出了bool可接受的范围,会引发OverflowError异常
#inc(b)
type
Day = enum
Monday, Tuesday, Wednesday
var d = Wednesday
dec(d) # 与inc相反,将值-1
echo d # Tuesday
# pred和dec一样,但返回一个新值
var d2 = pred(d)
echo d2
# succ和inc一样,但返回一个新值
d2 = succ(d2, 2)
echo d2 # Wednesday
inc、dec、succ、pred都支持第2个参数,指定一个跨度
var n = 0
echo n # 0
inc(n, 5)
echo n # 5
dec(n, 2)
echo n # 3
n = succ(n, 7)
echo n # 10
n = pred(n, 2)
echo n # 8
三、范围值
范围值需要自己定义,强制只接受范围内的值
type
MyRange = range[0..5]
var r: MyRange = 0
echo r
inc(r, 2)
echo r
上面这个例子自定义了一个MyRange类型,只接受0到5的数值
四、集合类型
集合类型用花括号构造"{}"
var
x: set[char] = {'a'..'f', '0'..'5'}
y = {'0'..'9'}
echo x # {'0', '1', '2', '3', '4', '5', 'a', 'b', 'c', 'd', 'e', 'f'}
echo y # {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9'}
# 合并集合
echo x + y # {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'}
# 交集
echo x * y # {'0', '1', '2', '3', '4', '5'}
# x不包含y的集合
echo x - y # {'a', 'b', 'c', 'd', 'e', 'f'}
# 集合是否相等
echo x == y # false
# x是否是y的子集,或相等
echo x <= y # false
# x集合中是否包含元素'z'
echo 'z' in x # false
# x集合中是否不包含元素'z'
echo 'z' notin x # true
# x集合中是否包含元素'z',同in一样
echo x.contains('z') # false
# 元素数量
echo y.card # 10
# 添加元素
incl(x, '6')
echo x # {'0', '1', '2', '3', '4', '5', '6', 'a', 'b', 'c', 'd', 'e', 'f'}
# 删除元素
excl(x, '0')
echo x # {'1', '2', '3', '4', '5', '6', 'a', 'b', 'c', 'd', 'e', 'f'}
五、数组类型
数组长度是固定的,无法改变,使用方括号"[]"
type
IntArray = array[1..5, int] # 下标从1开始,元素数量为5个
var arr: IntArray
arr = [5,10,15,20,25]
for index, val in arr:
echo "Index: ", index, " Value = ", val
输出结果
Index: 1 Value = 5
Index: 2 Value = 10
Index: 3 Value = 15
Index: 4 Value = 20
Index: 5 Value = 25
或者直接指定长度,下标默认从0开始
type
IntArray = array[5, int] # 下标从0开始,元素数量为5个
var arr: IntArray
arr = [5,10,15,20,25]
for index, val in arr:
echo "Index: ", index, " Value = ", val
echo low(arr) # 最小下标0
echo high(arr) # 最大下标4
echo len(arr) # 数组长度
echo repr(arr) # 打印数组内容 [5,10,15,20,25]
六、seq类型
seq类型其实就是动态数组
var arr: seq[int] # 不用指定size,默认为nil
echo arr
arr = @[5,10] # 赋值方式和数组一样用[],只是前面多了个@符号
echo arr
arr.add(15) # 添加元素
echo arr # [5, 10, 15]
arr.del(0) # 删除元素
echo arr # [10, 15]
arr.insert(5, 1) # 在索引1处插入元素5
echo arr # [15, 5, 10]
var
x: seq[int]
newSeq(x, 10) # 用newSeq方法生成指定长度的seq
echo x
七、OpenArray
怎么又来了个数组呢?别怕,它只能用在函数参数中,来个反面教材
proc foo(arr: array[3, int]): int = arr.len
var
arr: array[4, int] = [5,10,15,20]
echo foo(arr) # 类型不匹配
因为在Nim中,array类型必须指定长度,如果一个函数要接受array类型也必须指定长度,但是这样就没法处理任意长度的数组了,所以在这里可以用OpenArray类型来解决
proc foo(arr: openArray[int]): int = arr.len
var
arr: array[4, int] = [5,10,15,20]
echo foo(arr)
八、切片
切片就是对另一个数据进行截取,是一种特性
var
a = "hello world!"
# 以下三句效果是一样的
echo a.substr(0, 5) # hello
echo a[0..4] # hello
echo a[..4] # hello
# 以下三句效果是一样的
echo a.substr(6, a.len - 1) # world!
echo a[6..a.len - 1] # world!
echo a[6..^1] # world!
# 替换字符串
a[0..4] = "123456789"
echo a
九、元祖类型
元祖类型用圆括号"()"来构造
var
person: tuple[name: string, age: int]
person = (name: "jack", age: 18)
echo person
作为函数返回值时,可以分开接受
proc foo(): tuple[name: string, age: int] =
result = (name: "jack", age: 18)
let
(name, age) = foo() # 用圆括号接受拆包后的值
echo name # jack
echo age # 18
十、引用和指针
自定义一个对象,可以理解为C语言中的结构体
type
MyObj = object
name: string
age: int
var obj: MyObj
echo sizeof(obj) # sizeof(name) + sizeof(age) = 8
obj是在栈上分配的内存,类似于C语言中结构体,随着成员变量的增加,size也会增加。
通过ref关键字用来声明一个引用类型,引用类型是可以被自动回收的,不用担心内存泄漏问题
type
MyObj = object
name: string
age: int
var obj: ref MyObj # 引用类型,默认为nil
echo sizeof(obj) # size = 4
if (obj == nil):
echo "obj == nil"
obj = new MyObj # 通过new来创建实例
obj.name = "jack"
echo obj.name
而用ptr声明的类型是不会被Nim回收的,此时就像在写C代码一样,自己要注意释放问题
type
MyObj = object
name: string
age: int
var obj: ptr MyObj # nil
echo sizeof(obj) # size = 4
if (obj == nil):
echo "obj == nil"
obj = cast[ptr MyObj](alloc(sizeof(MyObj)))
obj.name = "jack"
echo obj.name
dealloc(obj) # 类似C语言中delete,需要手动释放内存
参考: