「singleton × thread」の編集履歴(バックアップ)一覧はこちら
「singleton × thread」(2010/12/28 (火) 17:25:22) の最新版変更点
追加された行は緑色になります。
削除された行は赤色になります。
* singleton と thread
#right{last update: &update(format=Y/m/d (D))}
Singleton とは,プログラム内でインスタンスが 1 つしか存在しないことを保証するクラスのこと. 要はグローバル変数の代わり.簡単なコードは以下の通り.
// singleton.h
#include <iostream>
#include <boost/thread.hpp>
class Singleton
{
private:
Singleton() {
std::cout << "Singleton : created" << std::endl;
}
Singleton(const Singleton&); // コピー禁止
Singleton& operator=(const Singleton&); // 代入禁止
public:
~Singleton() {
std::cout << "Singleton : deleted" << std::endl;
}
// インスタンス取得関数
static Singleton* getInstance();
};
// singleton.cpp
#include "singleton.h"
Singleton* Singleton::getInstance()
{
static Singleton instance;
return &instance;
}
さてここで疑問に思った.このインスタンス取得関数ってマルチスレッド安全なの?
調べると,「C では静的自動変数の初期化は,実行フローが最初に変数の宣言・初期化行を通過した時に行われる」とある.ならば Singleton のコンストラクタが何やら時間のかかる処理をやるとして,あるスレッドが Singleton のコンストラクタにいる間に他のスレッドがインスタンス取得関数を呼んだらどうなるんだろう.
てことで実験.
// singleton.h
#include <iostream>
#include <boost/thread.hpp>
class Singleton
{
private:
Singleton() {
// 1000 ミリ秒かかる処理
boost::thread::sleep(
boost::get_system_time()
+ boost::posix_time::milliseconds(1000));
std::cout << "Singleton : created" << std::endl;
}
Singleton(const Singleton&); // コピー禁止
Singleton& operator=(const Singleton&); // 代入禁止
public:
~Singleton() {
std::cout << "Singleton : deleted" << std::endl;
}
// インスタンス取得関数
static Singleton* getInstance();
};
// singleton.cpp
#include "singleton.h"
#include <cstdlib>
Singleton* Singleton::getInstance()
{
static Singleton instance;
return &instance;
}
void func()
{
std::cout << "func : begin" << std::endl;
// インスタンス取得関数の呼び出し
Singleton* singleton = Singleton::getInstance();
std::cout << "func : end" << std::endl;
}
int main(int argc, char* argv[])
{
boost::thread th1( &func );
boost::thread th2( &func );
boost::thread th3( &func );
th1.join();
th2.join();
th3.join();
return EXIT_SUCCESS;
}
結果.
func : begin
func : begin
func : begin
Singleton : created # この直前で1秒固まる
func : end
func : end
func : end
Singleton : deleted
マルチスレッド安全でした&footnote(あくまで gcc では.他の処理系では知りません.規格上はどうなってるんだろう…).なんだつまらん(笑)
&trackback()
----
**参考
-[[デザインパターン編第9章 Singleton パターン - Programming Place Plus>http://www.geocities.jp/ky_webid/design_pattern/009.html]]
-[[letsboost::thread>http://www.kmonos.net/alang/boost/classes/thread.html]]
----
**コメント
#comment(title_name=name,title_msg=comment)
----
**関連ページ
#related()
----
**関連ブログ
#blogsearch(singleton)
* singleton × thread
#right{last update: &update(format=Y/m/d (D))}
さて,この記事のテーマとは singleton と thread でどちらが攻めでどちらが○けか,''ではない!''
なんてタイトルをつけやがる….期待させて申し訳ないが(ありえない) Singleton とは,プログラム内でインスタンスが 1 つしか存在しないことを保証するクラスのこと. 要はグローバル変数の代わり.簡単なコードは以下の通り.
// singleton.h
#include <iostream>
#include <boost/thread.hpp>
class Singleton
{
private:
Singleton() {
std::cout << "Singleton : created" << std::endl;
}
Singleton(const Singleton&); // コピー禁止
Singleton& operator=(const Singleton&); // 代入禁止
public:
~Singleton() {
std::cout << "Singleton : deleted" << std::endl;
}
// インスタンス取得関数
static Singleton* getInstance();
};
// singleton.cpp
#include "singleton.h"
Singleton* Singleton::getInstance()
{
static Singleton instance;
return &instance;
}
さてここで疑問に思った.このインスタンス取得関数ってマルチスレッド安全なの?
調べると,「C では静的自動変数の初期化は,実行フローが最初に変数の宣言・初期化行を通過した時に行われる」とある.ならば Singleton のコンストラクタが何やら時間のかかる処理をやるとして,あるスレッドが Singleton のコンストラクタにいる間に他のスレッドがインスタンス取得関数を呼んだらどうなるんだろう.
てことで実験.
// singleton.h
#include <iostream>
#include <boost/thread.hpp>
class Singleton
{
private:
Singleton() {
// 1000 ミリ秒かかる処理
boost::thread::sleep(
boost::get_system_time()
+ boost::posix_time::milliseconds(1000));
std::cout << "Singleton : created" << std::endl;
}
Singleton(const Singleton&); // コピー禁止
Singleton& operator=(const Singleton&); // 代入禁止
public:
~Singleton() {
std::cout << "Singleton : deleted" << std::endl;
}
// インスタンス取得関数
static Singleton* getInstance();
};
// singleton.cpp
#include "singleton.h"
#include <cstdlib>
Singleton* Singleton::getInstance()
{
static Singleton instance;
return &instance;
}
void func()
{
std::cout << "func : begin" << std::endl;
// インスタンス取得関数の呼び出し
Singleton* singleton = Singleton::getInstance();
std::cout << "func : end" << std::endl;
}
int main(int argc, char* argv[])
{
boost::thread th1( &func );
boost::thread th2( &func );
boost::thread th3( &func );
th1.join();
th2.join();
th3.join();
return EXIT_SUCCESS;
}
結果.
func : begin
func : begin
func : begin
Singleton : created # この直前で1秒固まる
func : end
func : end
func : end
Singleton : deleted
マルチスレッド安全でした&footnote(あくまで gcc では.他の処理系では知りません.規格上はどうなってるんだろう…).なんだつまらん(笑)
&trackback()
----
**参考
-[[デザインパターン編第9章 Singleton パターン - Programming Place Plus>http://www.geocities.jp/ky_webid/design_pattern/009.html]]
-[[letsboost::thread>http://www.kmonos.net/alang/boost/classes/thread.html]]
----
**コメント
#comment_num2(size=40,vsize=10,num=20,logpage=コメントログ)
----
**関連ページ
#related()
----
**関連ブログ
#blogsearch(singleton)
表示オプション
横に並べて表示:
変化行の前後のみ表示: