4

問題

を使用sort_by_keyして渡される値で使用していますzip_iterator。これsort_by_keyは何度も呼び出され、特定の反復の後、10倍遅くなりますこのパフォーマンスの低下の原因は何ですか?

症状

を使用して3つのベクトルを並べ替えsort_by_keyていますが、そのうちの1つがキーベクトルとして機能します。

struct Segment
{
  int v[2];
};

thrust::device_vector<int> keyVec;
thrust::device_vector<int> valVec;
thrust::device_vector<Segment> segVec;

// ... code which fills these vectors ...

thrust::sort_by_key( keyVec.begin(), keyVec.end(),
                     make_zip_iterator( make_tuple( valVec.begin(), segVec.begin() ) ) );

ベクトルのサイズは通常約400万です。呼び出された最初の2回では、sort_by_key0.04秒かかり、ループ3では0.1秒かかり、残りのループではさらに0.3秒に低下します。したがって、パフォーマンスが10倍低下します。

追加情報

劣化の唯一の要因がであるようにするためにsort_by_key、上記を手書きカーネルを使用した手動ソートに置き換えました。

thrust::device_vector<int> indexVec( keyVec.size() );
thrust::sequence( indexVec.begin(), indexVec.end() );

// Sort the keys and indexes
thrust::sort_by_key( keyVec.begin(), keyVec.end(), indexVec.begin() );

thrust::device_vector<int> valVec2( keyVec.size() );
thrust::device_vector<Segment> segVec2( keyVec.size() );

// Use index array and move vectors to destination
moveKernel<<< x, y >>>(
  toRawPtr( indexVec ),
  indexVec.size(),
  toRawPtr( valVec ),
  toRawPtr( segVec ),
  toRawPtr( valVec2 ),
  toRawPtr( segVec2 ) );

// Swap back into original vectors
valVec.swap( valVec2 );
segVec.swap( segVec2 );

この手書きの並べ替えには0.03秒かかり、sort_by_keyやzip_iteratorで見られるパフォーマンスの低下とは異なり、このパフォーマンスはすべての反復で一貫しています。

4

1 に答える 1

1

各ループで正確なタイミングを得るには、各ループの最後で cudaThreadSynchronize を使用する必要があります。最初の 2 つのループで得られるタイミングは、探している実際のタイミングではない場合があります。

于 2011-04-22T19:03:21.530 に答える