私が見つけた唯一の機能は
(eval `(vector ,@(mapcar #'1+ [1 2 3 4])))
=> [2 3 4 5]
それはそうです遠く、あまりにも「正しい」方法であることが複雑。
私が見つけた唯一の機能は
(eval `(vector ,@(mapcar #'1+ [1 2 3 4])))
=> [2 3 4 5]
それはそうです遠く、あまりにも「正しい」方法であることが複雑。
回答:
cl-map
代わりにを使用してください:
(cl-map 'vector #'1+ [1 2 3 4])
少し余分な背景は:cl-map
あるのCommon Lisp map
関数は、シーケンス型に一般こと:
(cl-map 'vector #'1+ '[1 2 3 4]) ;; ==> [2 3 4 5]
(cl-map 'list #'1+ '(1 2 3 4)) ;; ==> (2 3 4 5)
(cl-map 'string #'upcase "abc") ;; ==> "ABC"
また、シーケンスタイプ間で変換することもできます(たとえば、ここでは、入力はリストであり、出力はベクトルです)。
(cl-map 'vector #'1+ '(1 2 3 4)) ;; ==> [2 3 4 5]
cl
、再調整されたcl-lib
ライブラリではなく、古いライブラリに関連していたと思います。私は、例えば、警告時にI得ることはありません(defun fnx () (cl-map 'vector #'1+ '[1 2 3 4]))
し、その後に(byte-compile 'fnx)
。
私は18秒もbeatられたので、clライブラリなしでこれを行うより簡単で安全な方法があります。また、要素を評価しません。
(apply #'vector (mapcar #'1+ [1 2 3 4])) ;; => [2 3 4 5]
cl-lib
依存関係を回避することに対するわずかな不便をトレードオフできます。
apply
。
(apply #'vector ...)
これまでに少し速くなると思いますが、完全を期すためにに置き換えることもできます(vconcat ...)
。
元のベクターがその後不要になり、メモリーの割り当てがタイムクリティカルである(たとえば、ベクターが大きい)場合には、それほどエレガントではないインプレースバリアントです。
(setq x [1 2 3 4])
(cl-loop for var across-ref x do
(setf var (1+ var)))
結果はに保存されx
ます。x
最後にフォームを返す必要がある場合はfinally return x
、次のように追加できます。
(cl-loop for var across-ref x do
(setf var (1+ var))
finally return x)
完全を期すために、次を使用しseq
ます。
(require 'seq)
(seq-into (seq-map #'1+ [1 2 3 4]) 'vector)
seq-into
行で削除された回答があります。ユーザーは、以下の理由のために彼の答えを削除しました:「seqのライブラリーは、基盤となるCommon Lispの拡張を使用しているため、私のソリューションはあまり関係あり- 8時53分でフォールクヴァング5月16日を。」
ループを使用できます
(let ((v (vector 1 2 3 4)))
(dotimes (i (length v))
(aset v i (1+ (aref v i))))
v)
;; => [2 3 4 5]
元のベクトルを変更したくない場合は、コピーを作成できます
(let* ((v0 (vector 1 2 3 4))
(v (copy-sequence v0)))
(dotimes (i (length v))
(aset v i (1+ (aref v i))))
(list v0 v))
;; => ([1 2 3 4] [2 3 4 5])
または、最初から新しいベクトルを作成します
(let* ((v0 (vector 1 2 3 4))
(v (make-vector (length v0) nil)))
(dotimes (i (length v))
(aset v i (1+ (aref v0 i))))
(list v0 v))
;; => ([1 2 3 4] [2 3 4 5])
cl
ライブラリはコンパイラ警告を発しませんか?(主にFSFが不快なためですか?)