2011-09-12 13 views
0

ベクトルが、私は次をコーディングするフォームベクトルのシーケンスを作成するC++

struct node 
     {string key; 
     int a,b; }; 

の構造のベクトルを意味:ユーザーが指定した数を考えるとはd私はシーケンスを作成したいと言いますdベクターv_1, v_2, ...v_d

v_1は、ユーザーデータから作成され、v_iからv_(i-1)i>=2です。 v_iサイズは別個keyフィールドとv_(i-1)内のノードの数です。 v_iノードの abフィールドはv(i-1)

どのように私はC++で効率的にこれをコーディングする必要があるのものの中からいくつかのブラックボックス化アルゴリズムに従って計算されますか? 私はint型のフィールドが1dの間で変化し、フォーム map<int, vector<nodes>>のマップを使うべき?

ありがとうございました!

P:S:私は1つの代わりのベクターを使用する、newオペレータといくつかのポインタ体操を使用して、溶液をコーディングすることができることを推測。しかし、私は可能な限りポインタを自由にしたいと思っています。

+0

連続でint型のキーを持つマップ?なぜベクトルのベクトルではないのですか? –

+0

連続?いいえ、キー値は離散1、...、dです。基本的には、対応するベクトルで整数を「ロック」する必要があります。すなわち「v_i」を有する「i」である。 – smilingbuddha

答えて

1

使用std::vector<std::vector<node> >が、回避するために、インテリジェントvector::reserve()を使用して再配分:

using std::vector; 
vector<vector<node>> v(d); // 0 nodes allocated, no wasted space yet 

using std::copy; 
using std::istream_iterator; 
using std::back_inserter; 
// Wish I could v[0].reserve(), but we don't have that info yet. 
copy(istream_iterator<node>(std::cin), istream_iterator<node>(), back_inserter(v[0])); 

// foreach v[1..d-1], compute v[i] from v[i-1] 
for(int i = 1; i < d; ++i) { 
    int size = ComputeSize(v[i-1]); // how big a list do we need? 
    v[i].reserve(size); // reserve the space for it, and 
    PopulateVectorFromVector(v[i-1], v[i]); // fill it in. 
} 

無駄な空間と時間を持つ唯一のベクトルをv [0]。


EDIT:上記 std::copyの呼び出しが

node tmp; 
while(std::cin >> tmp) { 
    v[0].push_back(tmp); 
} 

std::copyとほぼ同等ループレスイディオムである3つの引数を取ります。最初の二つは、第三の宛先を定義output iteratorあるが、我々は、コピー元の範囲を定義input iteratorsです。

具体的には、istream_iterator<node>(std::cin)は、逆参照されると、標準入力ストリームから次のnodeを読み込む入力イテレータです。 back_inserter(v[0])は、参照解除されて割り当てられたときにv[0].push_back()を呼び出す出力イテレータです。

+0

どのくらい予約していますか? –

+0

@Mooing - 私はもう一度コンパイルされていないコードを投稿するつもりはないと誓った。私はより明確に編集しました。 –

+0

ロブありがとうございました。私はあなたの提案を試してみます。コピー文の引数(イテレータとインサータ)の部分が多少C++のnoobであることは明らかではないが、その簡単な説明が参考になるだろう。 – smilingbuddha

2

あなたのコンテナ型として範囲0..d、なぜstd::vector<std::vector<node> >を必要と考えますか?

+0

はい、私はそれについて考えました。しかし、各ベクトルの大きさはあらかじめ分かっていません。私は、ベクトルが成長/サイズ変更できることは知っていますが、私の配列 'v_i'は非常に大きくなる可能性があるため、この成長/サイズ変更はアルゴリズムのパフォーマンスのボトルネックになります。したがって、私はそれを変更する前に特定のサイズのベクトルを作成したいと思っています。 – smilingbuddha

+0

@Gaurishでは、すべての要素を追加する前に空間を予約しておくことができます。各ベクトルの上限を知っていれば、それを使うことができます(最初のベクトル 'v_1'は決まっていません。 ]、私はあなたの質問を理解する - したがって、 'v_3..v_d'の構築をより簡単にする - すなわち、' v_(i-1) 'をコピーすることによって、後続のすべてのベクトルは同じキーセットを持つでしょう。 – Nim

+0

' std :: vector <> :: reserve'を使用して、ターゲットベクトルサイズについてのヒントを与えると、要素の追加は内部的にsize変数を変更し、その要素(両方ともO(1))を割り当てるだけです。 – eudoxos

関連する問題