2010-11-24 4 views
13

私は2次元リストと1次元リストを持っています。私は追加の列として2Dリストに1Dリストを挿入したいと思います。たとえば:テーブルの行に追加する

array = {{a,1,2},{b,2,3},{c,3,4}}; 
column = {x,y,z}; 

final = {{a,1,2,x},{b,2,3,y},{c,3,4,z}}; 

になり、私はinelegantlyこれを行っている:

Table[Insert[array[[i]], column[[i]], 4], {i, Length[array]}]; 

私の質問:Mathematicaでこれを実行するための適切な方法は何ですか?私はそれが私が使用しているループが必要とは思わない。私の解決策は醜いと感じています。例えば

答えて

14

:また、行うことができます

[email protected][[email protected], column] 

はそうのような関数である:あなたが頻繁にそれを使用する必要がある場合

subListAppend = [email protected][[email protected]#1, #2] &; 
subListAppend[array, column] 

それが容易になりますました。もちろん、最後以外の場所に挿入する場合は、Insert[]を使用することができます。

subListInsert = [email protected][[email protected]#1, #2, #3] &; 
subListInsert[array, column, 2] 
--> {{a, x, 1, 2}, {b, y, 2, 3}, {c, z, 3, 4}} 

EDIT:義務速度最適化の議論が開始されているので、ここではthisと10000x200アレイを使用して、いくつかの結果である:

[email protected]{{array, List /@ column}}:    0.020 s 
[email protected][[email protected], column]:   0.067 s 
MapThread[Append, {array, column}]:     0.083 s 
MapThread[Insert[#1, #2, 4] &, {array, column}]: 0.095 s 
Map[Flatten, Flatten[{array, column}, {2}]]:  0.26 s 
ConstantArray based solution:      0.29 s 
Partition[[email protected][{array, column}], 4]: 0.48 s 

は、そして勝者はArrayFlattenです!それは追加の変数を必要とするが

+1

よしは、ありがとうございました!今私はそれを理解するためにそれを選ぶ必要があります*なぜ、しかしそれは私のためです。 –

+0

一度に1つの要素に移動します(たとえば、Transpose @ arrayが何をするかを参照してください)。 – Timo

+0

うん、それは助けた。折り紙のようなものです。私はMathematicaと不必要に戦っていることを知っていました。再度、感謝します。 –

5

もう一つの可能​​性は、より速く、大きな数値行列のために自分のコンピュータ上にあるように思わ

result = ConstantArray[0, Dimensions[array] + {0, 1}]; 
result[[All, 1 ;; Last[Dimensions[array]]]] = array; 
result[[All, -1]] = column; 

です。実数のエントリを扱っている場合は、使用することをお勧めします。

result = ConstantArray[0.0, Dimensions[array] + {0, 1}]; 

スピードの向上を維持します。

も(IMOとエレガント)高速ですが、結果を解凍します

MapThread[Append, {array, column}] 

もあります。 (しかし、あなたは例のようにシンボリックエントリを持っている場合、それは問題にならないのです。)

+0

Brettに感謝します。あなたのMapThreadの使用法は本当にエレガントです。私はトランスコンポジションの答えを最初に見たことがうれしく思っています。なぜなら、それが使用するコンセプトがより広く適用できるという気持ちがあるからですが、これは非常に簡潔です。私の行列は、ConstantArrayのアプローチのための余分なコード行を保証するのに十分な大きさではなく、主にシンボリックデータを含んでいます。それでも、同じ問題に対する全く異なる4つのアプローチ、つまりMathematica! –

+0

興味深いことに、私の方法を使って、OPの例を使って「タイミング」を約35%向上させ、大きな(1k - 1Mエントリ)マトリックスについては約10倍向上させることができました。カーネルレベルでのほとんどの異なるリスト操作は、同じ(非常に最適化された)コードによって実行されるので、MMAに何らかの方法(他の言語では正しい/最適であるかもしれない)を強いるようにするために、ほとんどの時間がオーバーヘッドにつながります。 – Timo

+0

OS XでV8でテストしていました。 –

2

それでもこの程度

k= Partition[[email protected][{#, {x, y, z}}], 4]& 

[email protected] {{a, 1, 2}, {b, 2, 3}, {c, 3, 4}} 

(* 
-> {{a, 1, 2, x}, {b, 2, 3, y}, {c, 3, 4, z}} 
*) 
+0

5つのアプローチを行います。これはソーセージのようなものです:あなたはそれを食べることができますが、あなたはそれがどのように作られているか見たくありません:) –

3

どのように?

pos = 4; 
MapThread[Insert[#1, #2, pos] &, {array, column}] 
3

「ぼろぼろ」の配列で動作するため、(時には)Flattenで転置するのが好きです。

Map[Flatten, Flatten[{array, column}, {2}]] 

{{1,2、X}、{B、2、3、Y}、{C、3、4、Z}}

を与えるしかし、もし、言う、カラムはわずか2要素

{{1,2、X}、{B、2、3、Y}、{C、3、4}}

を与える

column2 = {x, y}; 
Map[Flatten, Flatten[{array, column2}, {2}]] 

を有します

(トランスポーズはここでは動作しません)

5

ここでは、それは前述のプログラムの中で最速の1に匹敵するかもしれない

In[11]:= Join[array,List/@column,2] 
Out[11]= {{a,1,2,x},{b,2,3,y},{c,3,4,z}} 

に参加しましょ使用して、私の試みです。ここ

+0

+1とてもいいです!はっきり明快です。 –

+0

「Join」メソッドは、これを行うための最も自然で(効率的な)方法のように思われるので、このページにはまだありません。 +1 –

1

現存する方法のいくつかのように実用的または効率的ではないが、リストに追加するには2つ以上ある:トリックをした

ArrayPad[array, {0,{0,1}}, List /@ column] 

PadRight[array, Dimensions[array] + {0, 1}, List /@ column] 
関連する問題