0

私は WCF での状態/同時実行管理の初心者です。以下のようなサービスクラスがあるとしましょう:

    [ServiceBehavior(InstanceContextMode = InstanceContextMode.Single, ConcurrencyMode = ConcurrencyMode.Multiple)]
        public class Service1 : IService1
        {
            private int _myCounter;
            private MyType _myType;
            private static MyType _myTypeStatic;
            private static Dictionary<string,string> _d = new Dictionary<string,string>();


            public void Method1()
            {
                // logic to set _myType
                // logic to set _myCounter

                // logic to set _myTypeStatic
                // logic to set _d

            }
            public void Method2()
            {
                // logic to save _myType, set in Method1() to db
                // logic to save _myCounter, set in Method1() to db

                // logic to save _myTypeStatic, set in Method1() to db
                // logic to save _d, set in Method1() to db    
            }
        }

2 つのクライアント接続が同時にこのサービスを消費する場合、それらは 2 つの異なるスレッドで実行されます。サービスのインスタンスしかないため、このシナリオで 2 つのグローバル クラス レベル変数の状態はどのように変化しますか? 静的変数と型に対してどのように機能しますか? これらの 2 つのスレッドが変数データの 2 つの異なるコピーを持っている可能性はありますが、まだ 1 つのサービス インスタンスで動作していますか?

4

2 に答える 2

0

まず、すべての変数はクリティカル セクションでスレッド セーフにする必要があります。InstanceContextMode.Single を設定しなくても、静的変数はすべてのインスタンスで共有されます。クラス変数は、そのインスタンスに入るすべてのスレッドで共有されます。ConcurrencyMode.Multiple は、複数のスレッドが開始できることを示します。さらに、クリティカル セクションを適用しても、使用しているロジックも機能しません。その場合、スレッドはデータを設定し、クリティカル セクションを解放して戻ります。別の呼び出しを行ってデータを保存しようとする前に、別のスレッドがデータをオーバーライドできます。これは、1 回の操作でデータを保存する必要があることを意味します。または、データをしばらく設定してから保存したい場合は、データをハッシュテーブルに保存することになります。方法1のように、クリティカル セクションを使用してデータを設定し、一意のキーを配置してクライアント ID などのデータのキーを設定し、クライアントがそれを認識していない場合はキーをクライアントに返します。次に、方法 2 でクライアントがキーを渡します。キーを使用してハッシュ テーブルにアクセスし、クライアントを使用してデータを取得して保存します。

于 2012-10-26T08:33:02.770 に答える
0

おそらく、変数セットを格納するクラスまたは構造体を定義し、それをメソッドに渡すだけですか?

public class Storage
{
    public Storage(int myCounter, MyType myType)
    {
        _myCounter = myCounter;
        _myType = myType;
    }
    public int _myCounter;
    public MyType _myType;
}

...

[ServiceBehavior(InstanceContextMode = InstanceContextMode.Single, ConcurrencyMode = ConcurrencyMode.Multiple)]
public class Service1 : IService1
{
    public void Method1(Storage st)
    {
        // logic to set _myType
        // logic to set _myCounter
    }
    public void Method2(Storage st)
    {
        // logic to save _myType, set in Method1() to db
        // logic to save _myCounter, set in Method1() to db
    }
}

このように、 Service1 は直接接続されていないデータに対して機能します。ただし、すべての呼び出し元はそのデータを「処理」する必要があります。たとえば、どこかに Storage st を保存します。

于 2012-10-26T08:23:18.233 に答える