1

私の割り当てでは、出力する変数を返すヒープ削除関数を使用する必要があることを知っています。しかし、割り当ての要件は非常にあいまいであり、誰かが私にもっと良い説明をしてくれるかどうか興味がありました。2番目または3番目の引数の使用方法についてはかなり混乱しています。並べ替えが必要で、2つのforループが必要ですが、その後は迷子になります。課題の内容は次のとおりです。

template <class T, class P> void print_list (vector<T>&, 
    const int, const int, P); 

この関数は、ヒープ構造からアイテムを取得し、それらをstdoutに出力します。ヒープ構造から単一のアイテムを取得するには、remove関数を呼び出します。この関数の最初の引数はヒープ構造のベクトル、2番目の引数はstdoutに割り当てられた印刷アイテムのサイズ、3番目の引数は1行の印刷アイテムの最大数、最後の引数は述語です。 。

これが私のコードです:

#include "340.h"

#ifndef H_PROG7
#define H_PROG7

// data files

#define D1 "prog7.d1"
#define D2 "prog7.d2"
#define D3 "prog7.d3"

#define INT_SZ 4    // width of integer
#define FLT_SZ 7    // width of floating-pt number
#define STR_SZ 12   // width of string

#define INT_LN 15   // no of integers on single line
#define FLT_LN 9    // no of floating-pt nums on single line
#define STR_LN 5    // no of strings on single line

// function prototypes

template<class T,class P> void insert(vector<T>&, const T&, P);
template<class T,class P> T remove(vector<T>&, P);

template<class T,class P> void upheap(vector<T>&, int, P);
template<class T,class P> void downheap(vector<T>&, int, P);

template<class T,class P>
void get_list(vector<T>&, const char*, P);

template<class T,class P>
void print_list(vector<T>&, const int, const int, P);

template<class T, class P>
void get_list(vector<T>& v, const char* file, P func) {
ifstream inFile("file");
T data;

while(inFile >> data) {
  inFile >> data;
  insert(v, data, func);
}
}

template<class T, class P>
void insert(vector<T>& v, const T& data, P func) {
v.push_back( data );
upheap( v, v.size()-1, func );
}

template<class T,class P>
void upheap(vector<T>& v, int start, P func) {

while( start <= v.size()/2 )   {

  unsigned int parent = start / 2;

  if( parent - 1  <= v.size() && v[parent - 1] > v[parent] )
     parent = parent - 1;

  if( v[start] <= v[parent] )
     break;

  swap( v[start], v[parent] );
  start = parent;
}
}

template<class T,class P>
void downheap(vector<T>& v, int start, P func) {

while(start <= v.size()/2 )   {

  unsigned int child = 2 * start;

  if( child + 1 <= v.size() && v[child + 1] > v[child])
     child = child + 1;

  if( v[start] >= v[child] )
     break;

  swap( v[start], v[child] );
  start = child;
}
}

template<class T,class P>
T remove(vector<T>& v, P func) {
swap( v[0], v.back() );
T& item = v.back();

v.pop_back();
downheap( v, 1, func );

return item;
}

template<class T,class P>
void print_list(vector<T>& v, const int size, const int line, P func) {

for(int i = 1; i < v.size(); i++) {
  cout << remove(v, func) << " ";
}
}

#endif
4

1 に答える 1

0

私が収集できることから、2番目のパラメーターは、リスト内の1つの要素が印刷されるときに使用できるスペースの数であるように見えます。3 番目のパラメーターは、1 行に印刷できる要素の数です。print_list 関数では、このパラメーターに基づいて次の行に移動する必要があるかどうかを判断するために、印刷した要素の数を追跡する必要があります。これらの両方を使用すると、出力を適切に配置できるはずです。出力の書式設定を行う方法を調べる必要があります。

例えば。リスト = [1, 9, 14, 2000, 244, 777, 3, 98102, 88, 53, 14]、サイズ = 6、行 = 3 出力:

     1     9    14
  2000   244   777
     3 98102    88
    53    14

最後のパラメーターは述語であり、実際にはどの関数でも使用していないようです (パラメーターをまったく使用していないときに何か間違ったことをしている兆候)。述語関数パラメーターは、渡される型 T に固有の何かを行うために使用する必要があります。たとえば、print_list では、型 T の変数を出力するために使用する必要があります。現在行っている方法で要素を出力する場合、タイプが正しく印刷されるという保証はありません。もちろん、int や double などの基本的な型でも機能しますが、いくつかの異なるメンバーを持つ型を想像してみてください。他の関数でもこの述語をどのように使用する必要があるか考えてみてください。オブジェクトを '<' または '>' で比較できますか?

于 2010-11-04T16:54:28.290 に答える