ワーカースレッドのスリープを制御するように、そしてスレッドがタスク・スケジューラー領域にジョインしたときや離脱したときを監視するように、task_scheduler_observer クラスが拡張されました。以前の task_scheduler_observer は、ワーカースレッドがグローバル・タスク・スケジューラーにジョインしたときと終了したときのみ監視していました。
task_scheduler_observer は、浮動小数点設定の管理には適していません。この目的で使用した場合の動作は不定です。詳細は、「浮動小数点設定」セクションを参照してください。
class task_scheduler_observer;
#define TBB_PREVIEW_LOCAL_OBSERVER 1 #include "tbb/task_scheduler_observer.h"
namespace tbb { class task_scheduler_observer { public: explicit task_scheduler_observer( bool local = false ); explicit task_scheduler_observer( task_arena & a ); // ローカル・オブザーバーに関連しないメソッドについては // task_scheduler_observer を参照 ... #if TBB_USE_PREVIEW_BINARY enum { keep_awake = false, allow_sleep = true }; // プレビューバイナリーを使用する機能のみ virtual bool may_sleep() { return allow_sleep; } #endif }; }
次のサンプルは、ワーカースレッドをハードウェア・スレッドに関連付けるオブザーバーのコードを示します。
class pinning_observer: public tbb::task_scheduler_observer { public: affinity_mask_t m_mask; // この領域で使用する HW アフィニティー・マスク pinning_observer( tbb::task_arena &a, affinity_mask_t mask ) : tbb::task_scheduler_observer(a), m_mask(mask) { observe(true); // オブザーバーをアクティブ化 } /* オーバーライド */ void on_scheduler_entry( bool worker ) { set_thread_affinity(tbb::this_task_arena::current_thread_index(), m_mask); } /* オーバーライド */ void on_scheduler_exit( bool worker ) { } };
次のサンプルは、ワーカースレッドの構築中はスリープ状態にならないようにして、オブザーバーを破棄した後にスリープを許可する、オブザーバーのコードです。このオブザーバーを使用して並列計算を継続する範囲を表すことができます。
class computation_scope: public tbb::task_scheduler_observer { public: computation_scope( ) { observe(true); } // オブザーバーをアクティブ化 /* オーバーライド */ bool may_sleep( ) { return keep_awake; } }; void usage() { non_TBB_code(); { computation_scope protector(); // ワーカースレッドをアクティブなまま保つ for(int i = 0; i < N; i++) tbb::parallel_for(0, M, ProcessingFunctor()); } non_TBB_code(); }
メンバー | 説明 |
---|---|
explicit task_scheduler_observer( bool local = false ) | インアクティブ状態 (監視が無効な状態) の task_scheduler_observer オブジェクトを構築します。local が false の場合、task_scheduler_observer のグローバル・セマンティクスと同じです。local が true で、オブザーバーがアクティブな場合、スレッドがタスク領域に追加されると、そのタスク領域のスレッドのみ通知を受け取ります。そして、タスク領域を離れるときも、スレッドは通知を受け取ります。 |
explicit task_scheduler_observer( task_arena & ) | 指定された task_arena に関連付けられたインアクティブ状態 (監視が無効な状態) の task_scheduler_observer オブジェクトを構築します。そして、指定されたタスク領域に関連する通知のみ受け取ります。 注このようなオブジェクトに対する observe(true) の呼び出しは、指定された task_arena オブジェクトの内部タスク領域の初期化を強制します。 |
virtual bool may_sleep() | コールバックは、ワーカースレッドがスリープ状態になる前に、ワーカースレッドのグローバル・オブザーバーで呼び出されます。keep_awake が返された場合、スレッドは直ちにスリープ状態になる代わりに新しいワークを積極的に探します。 注コールバックは、同じスレッドにより、ほかのスレッドと同時に、周期的に呼び出すことができます。ローカル・オブザーバー・モードやマスタースレッドに対しては呼び出されず、ワーカースレッドがリソース・マネージャーに無条件にリターンする場合にも呼び出されません。スレッドは、on_scheduler_entry() などのほかのコールバックの前に may_sleep() を呼び出すことができます。注このメソッドを有効にするには、アプリケーションをプレビュー・ライブラリーとリンクする必要があります。 |