<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="ja">
	<id>https://monobook.org/w/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=126.212.131.37</id>
	<title>MonoBook - 利用者の投稿記録 [ja]</title>
	<link rel="self" type="application/atom+xml" href="https://monobook.org/w/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=126.212.131.37"/>
	<link rel="alternate" type="text/html" href="https://monobook.org/wiki/%E7%89%B9%E5%88%A5:%E6%8A%95%E7%A8%BF%E8%A8%98%E9%8C%B2/126.212.131.37"/>
	<updated>2026-06-07T10:38:54Z</updated>
	<subtitle>利用者の投稿記録</subtitle>
	<generator>MediaWiki 1.42.1</generator>
	<entry>
		<id>https://monobook.org/w/index.php?title=%E3%83%80%E3%83%96%E3%83%AB%E3%83%BB%E3%83%81%E3%82%A7%E3%83%83%E3%82%AF%E3%83%BB%E3%83%AD%E3%83%83%E3%82%AD%E3%83%B3%E3%82%B0&amp;diff=2738</id>
		<title>ダブル・チェック・ロッキング</title>
		<link rel="alternate" type="text/html" href="https://monobook.org/w/index.php?title=%E3%83%80%E3%83%96%E3%83%AB%E3%83%BB%E3%83%81%E3%82%A7%E3%83%83%E3%82%AF%E3%83%BB%E3%83%AD%E3%83%83%E3%82%AD%E3%83%B3%E3%82%B0&amp;diff=2738"/>
		<updated>2014-10-26T01:29:17Z</updated>

		<summary type="html">&lt;p&gt;126.212.131.37: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&#039;&#039;&#039;ダブル・チェック・ロッキング&#039;&#039;&#039;（[[英語]]：Double Check Locking）とは、マルチスレッド環境下における[[変数]]に対して、初回は[[ロック]]せず状態チェックを行い、そこで必要であれば再度[[ロック]]を掛けたのちに状態チェックを行うという[[ソフトウェア]]の[[最適化]]技法、[[デザインパターン]]のひとつである。&lt;br /&gt;
&lt;br /&gt;
[[変数]]の[[ロック]]は非常に[[オーバーヘッド]]の大きい重たい処理であるため、その発生回数を可能な限り減らすことで[[プログラム]]の高速化を実現しようというものである。&lt;br /&gt;
&lt;br /&gt;
ダブル・チェック・ロッキングは、主に[[マルチスレッド]]環境下での[[シングルトンパターン]]を実装する際に[[オーバーヘッド]]の低減を目的として使われることが多い。&lt;br /&gt;
&lt;br /&gt;
== 主なプログラミング言語での実装例 ==&lt;br /&gt;
=== C# ===&lt;br /&gt;
[[C Sharp|C#]]における標準的なダブル・チェック・ロッキングの実装方法を示す。この記述方法では[[C Sharp|C#]]のキーワードのひとつであるvolatileを用いているのがミソである。なおvolatileキーワードと同等の機能を提供していない[[.NET Framework]]系の[[プログラミング言語]]も多く、それらでは別の実装方法を検討する必要がある。&lt;br /&gt;
&amp;lt;source lang=&amp;quot;csharp&amp;quot;&amp;gt;&lt;br /&gt;
public class MySingleton&lt;br /&gt;
{&lt;br /&gt;
    private static object _sync = new object();&lt;br /&gt;
    private static volatile MySingleton _instance = null;&lt;br /&gt;
&lt;br /&gt;
    // プライベートコンストラクター&lt;br /&gt;
    // ※本クラスを除き、newキーワードによるインスタンス生成を出来なくする。&lt;br /&gt;
    private MySingleton()&lt;br /&gt;
    {&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    // &lt;br /&gt;
    public static MySingleton GetInstance()&lt;br /&gt;
    {&lt;br /&gt;
        // 1回目のチェック&lt;br /&gt;
        // ロックしていないので高速に処理される&lt;br /&gt;
        if (null == _instance)&lt;br /&gt;
        {&lt;br /&gt;
            // ロック&lt;br /&gt;
            // ※このブロック内はクソ重い&lt;br /&gt;
            lock (_sync)&lt;br /&gt;
            {&lt;br /&gt;
                // 2回目のチェック&lt;br /&gt;
                if (null == _instance)&lt;br /&gt;
                {&lt;br /&gt;
                    _instance = new MySingleton();&lt;br /&gt;
                }&lt;br /&gt;
            }&lt;br /&gt;
        }&lt;br /&gt;
        return _instance;&lt;br /&gt;
    }&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== C# (Lazy) ===&lt;br /&gt;
[[.NET Framework 4.0]]では、標準でLazy&amp;lt;T&amp;gt;クラスが用意されており、それを使うことでよりシンプルにダブル・チェック・ロッキングを記述できるようになった&amp;lt;!--&amp;lt;ref&amp;gt;{{cite &lt;br /&gt;
 |title=C# 4.0 in a Nutshell&lt;br /&gt;
 |last=Albahari&lt;br /&gt;
 |first=Joseph &lt;br /&gt;
 |isbn=0596800959&lt;br /&gt;
 |year=2010&lt;br /&gt;
 |publisher=O&#039;Reilly Media&lt;br /&gt;
 |chapter=Threading in C#: Using Threads&lt;br /&gt;
 |chapterurl=http://www.albahari.com/threading/part3.aspx#_LazyT&lt;br /&gt;
 |quote=&amp;lt;code&amp;gt;Lazy&amp;amp;lt;T&amp;amp;gt;&amp;lt;/code&amp;gt; actually implements […] double-checked locking. Double-checked locking performs an additional volatile read to avoid the cost of obtaining a lock if the object is already initialized.&lt;br /&gt;
}}&amp;lt;/ref&amp;gt;--&amp;gt;。&lt;br /&gt;
この記述方法は[[C Sharp|C#]]に依存した機能も特に使われておらず、[[.NET Framework]]系の様々な[[プログラミング言語]]へも特に悩むことなく移植・実装可能であると思われる。&lt;br /&gt;
&amp;lt;source lang=&amp;quot;csharp&amp;quot;&amp;gt;&lt;br /&gt;
using System;&lt;br /&gt;
&lt;br /&gt;
public class MySingleton&lt;br /&gt;
{&lt;br /&gt;
    private static readonly Lazy&amp;lt;MySingleton&amp;gt; _instance  &lt;br /&gt;
        = new Lazy&amp;lt;MySingleton&amp;gt;(() =&amp;gt; new MySingleton());&lt;br /&gt;
&lt;br /&gt;
    private MySingleton()&lt;br /&gt;
    {&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    public static MySingleton GetInstance()&lt;br /&gt;
    {&lt;br /&gt;
        return _instance.Value;&lt;br /&gt;
    }&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Java ===&lt;br /&gt;
[[Java]]では[[仕様]]において[[アウトオブオーダー]]を用いるメモリモデルが可能となっていたため、この[[イディオム]]を使うことには問題があり、一部の[[実装]]では実際に正しく働かない可能性があることが知られている。詳細は http://www.ibm.com/developerworks/jp/java/library/j-dcl/ を参照。&lt;br /&gt;
&lt;br /&gt;
[[Java]]では絶対にダブルチェックロッキングを使用してはならない。&lt;br /&gt;
&lt;br /&gt;
たとえば以下のような[[Java]]の[[ソースコード]]があったとする。&lt;br /&gt;
&amp;lt;source lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
Person hage = new Person();&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
これが一部のJava実装では以下のような動作になる。&lt;br /&gt;
# [[メモリ]]上に[[インスタンス]]が確保さる。&lt;br /&gt;
#: hage[[変数]]自体は[[null]]ではなくなる。&lt;br /&gt;
# [[コンストラクタ]]は実行されない。&lt;br /&gt;
#: [[コンストラクタ]]が実行されるタイミングは、オリジナル（newを実行した[[スレッド]]の持つ）インスタンスに対して外部から[[メンバー関数]]や[[メンバー変数]]に初回アクセスがあったとき。これを[[遅延初期化]]（lazy initialization）という。これによりhage[[変数]]自体は[[null]]ではないので後続スレッドはコンストラクタを実行していない不完全な[[インスタンス]]の[[参照]]を取得できてしまう。&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
public static Singleton getInstance()&lt;br /&gt;
{&lt;br /&gt;
    // 1: 先行スレッドから見た場合はnull&lt;br /&gt;
    //&lt;br /&gt;
    // 3: 後続スレッドから見た場合は非null、&lt;br /&gt;
    //    ただしコンストラクタが実行されていない不完全なものである場合がある。&lt;br /&gt;
    if (instance == null)&lt;br /&gt;
    {&lt;br /&gt;
        synchronized(Singleton.class)&lt;br /&gt;
        {&lt;br /&gt;
            if (instance == null)&lt;br /&gt;
            {&lt;br /&gt;
                // 2:&lt;br /&gt;
                // 先行スレッドによりメモリが割り当てられてnullではなくなるが、&lt;br /&gt;
                // この時点でコンストラクタは実行されていない。&lt;br /&gt;
                instance = new Singleton();&lt;br /&gt;
            }&lt;br /&gt;
        }&lt;br /&gt;
    }&lt;br /&gt;
    return instance;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== 関連項目 ==&lt;br /&gt;
* [[マルチスレッド]]&lt;br /&gt;
* [[並列処理]]&lt;br /&gt;
* [[デザインパターン]]&lt;br /&gt;
&lt;br /&gt;
== 参考文献 ==&lt;br /&gt;
{{reflist}}&lt;br /&gt;
&lt;br /&gt;
{{stub}}&lt;/div&gt;</summary>
		<author><name>126.212.131.37</name></author>
	</entry>
</feed>