• 泛型

    泛型

    泛型是Nim用 类型形参 参数化过程、迭代器或类型的方法 。 根据上下文,括号用于引入类型形参或实例化泛型过程、迭代器或类型。

    以下示例显示了可以建模的通用二叉树:

    1. type
    2. BinaryTree*[T] = ref object # 二叉树是左右子树带有泛型形参 ``T`` 的泛型类型,其值可能为nil
    3. le, ri: BinaryTree[T]
    4. data: T # 数据存储在节点中。
    5.  
    6. proc newNode*[T](data: T): BinaryTree[T] =
    7. # 构造一个节点
    8. result = BinaryTree[T](le: nil, ri: nil, data: data)
    9.  
    10. proc add*[T](root: var BinaryTree[T], n: BinaryTree[T]) =
    11. # 把节点插入到一颗树
    12. if root == nil:
    13. root = n
    14. else:
    15. var it = root
    16. while it != nil:
    17. # 比较数据项;使用泛型 ``cmp`` proc,适用于任何具有``==``和````运算符的类型
    18. var c = cmp(it.data, n.data)
    19. if c < 0:
    20. if it.le == nil:
    21. it.le = n
    22. return
    23. it = it.le
    24. else:
    25. if it.ri == nil:
    26. it.ri = n
    27. return
    28. it = it.ri
    29.  
    30. proc add*[T](root: var BinaryTree[T], data: T) =
    31. # 便利过程:
    32. add(root, newNode(data))
    33.  
    34. iterator preorder*[T](root: BinaryTree[T]): T =
    35. # 前序遍历二叉树
    36. # 由于递归迭代器尚未实现,因此它使用显式堆栈(因为更高效):
    37. var stack: seq[BinaryTree[T]] = @[root]
    38. while stack.len > 0:
    39. var n = stack.pop()
    40. while n != nil:
    41. yield n.data
    42. add(stack, n.ri) # 将右子树推入堆栈
    43. n = n.le # 跟着左指针
    44.  
    45. var
    46. root: BinaryTree[string] # 使用 ``string`` 实例化二叉树
    47. add(root, newNode("hello")) # 实例化 ``newNode`` 和 ``add``
    48. add(root, "world") # 实例化第二个 ``add`` proc
    49. for str in preorder(root):
    50. stdout.writeLine(str)

    T 被称为 泛型类型形参 或 类型变量 。