可扩展的矢量类型

时间:2017-01-20 19:39:27

标签: vector common-lisp adjustable-array

如何正确指定可扩展向量的common-lisp类型(即,vector-push-extend可接受),因此可以复制它。例如,如果向量由以下定义:

(defparameter v (make-array 2
                            :initial-contents '((a (b)) (c (d) e))
                            :adjustable t
                            :fill-pointer t))

我复制它的简单(不正确)方法是:

(map 'array #'copy-tree v)

但这会在sbcl中生成类型错误。可以使用正确的序列类型规范吗?

2 个答案:

答案 0 :(得分:5)

简单复制

你可以这样做:

(map (type-of v) #'copy-tree v)

什么类型?

CL-USER> (type-of v)
(VECTOR T 2)

以下就足够了:

(map 'vector #'copy-tree v)

This graph有助于记住类型层次结构,尤其是数组和向量。

可调节,填充指针,......

但是,生成的矢量不可调整。也许这样的事情会有所帮助:

(defun my-copy (vector)
  (map-into (make-array (array-dimensions vector)
                        :adjustable (adjustable-array-p vector)
                        :fill-pointer (fill-pointer vector))
            #'copy-tree
            vector))

答案 1 :(得分:3)

MAP需要输入序列类型说明符ARRAY不是一个。 SEQUENCE的子类型的示例包括VECTORLIST

VECTOR的类型声明语法为:vector [{element-type | *} [{size | *}]]

无法在矢量类型声明中指定可调填充指针置换等...等功能。相应的功能选项也不作为函数make-sequence的关键字提供。 copy-seq也不会创建具有此类功能的向量。要创建此类向量,您必须使用MAKE-ARRAY

因此选项是:

  • 也许矢量类型足够
  • 对于具有特殊功能的矢量,请通过MAKE-ARRAY创建并使用MAP-INTO - >等功能看到coredump的优秀答案。