2011-11-07 4 views
0

私はちょうど次のコードを見つめていて、本当に12行のソースを埋める必要があるのか​​疑問に思っていました。フィールドへの簡単なインターフェイスのこれらのオプションの違いは何ですか?

private static IUnityContainer _container; 
    public static IUnityContainer Container 
    { 
     get 
     { 
      return _container; 
     } 
     set 
     { 
      _container = value; 
     } 
    } 

私の考えは、なぜただ一つではないのでしょうか?

public static IUnityContainer Container; 

私は、これは、コンディショニングに膝ジャーク反応のより..です答えは「あなたはカプセル化を解除することはできません」のようなものだと思う、または他のいくつかの理由があり、微妙かそうでありませんか?

+1

これはまったく同じです。詳細については、[こちら](http://stackoverflow.com/questions/7280502/c-sharp-automatic-properties-are-they-safe-for-enterprise-development/7280544#7280544)を参照してください。 – CodeCaster

+3

全く同じではありません。ここで彼はフィールドVSについて話していますが、これは単純なGoogleを介して何百ものディスカッションがあります。あなたのリンクは自動プロパティとその違いについて話します。 –

+1

@CodeCasterまったく同じではありません。あなたのリンクは、実装されたマニュアルと同じであることを示していますが、この質問ではフィールドとプロパティです。 – DanielB

答えて

2

まあ、GetType()、GetProperty( "Container" ...)などのようないくつかの変わった方法でリフレクションを使用したくない場合は、欠点はありません。

しかし、フィールドを公開することは汚れていると考えられ、プロパティは通常、純粋な観点からはよりクリーンです。

FxCopは素晴らしいことではないことを警告しますが、欠点はありません。

あなたが同じ時間に短いがきれいになりたい場合は、あなただけの自動プロパティを使用することができます

public static IUnityContainer Container { get; set; } 

自動プロパティをしかし、コンパイラのバージョン3.0以降のみ動作します。

ある可能性のある欠点は、あるフィールドで、たとえば、Interlocked.Exchange(ref MyClass.MyStaticField, null); のように、フィールドまたはbyrefをそのフィールドに渡す場合です。今後プロパティで変更した場合はもう機能しませんので注意してくださいそのフィールドを参照渡ししません。最初からプロパティを使用するだけであれば、この問題は発生しません。 この問題はstatic readonlyフィールドでは発生しません。これらのフィールドは参照渡しできません。静的な読み取り専用フィールドの使用は非常に一般的です。

プロパティの代わりに絶対にフィールドを使用しない状況は、リモート処理(RPC、リモートプロシージャコール)に使用されるMarshalByRefObjectを継承するクラスを持つ場合です。

ここで私は例を挙げていますが、問題はインスタンスフィールドであり、静的フィールドではないため、あなたのケースではありません。

public class MyClass : 
    MarshalByRefObject 
{ 
    public int MyValue; 
} 

class Program 
{ 
    static void Main(string[] args) 
    { 
     var obj = new MyClass(); 

     // This will give you warning CS1690: Accessing a member on 'MyValue' may cause a runtime exception because it is a field of a marshal-by-reference class 
     Console.WriteLine(obj.MyValue.ToString()); 
    } 
} 

リモートプロシージャコールは、MarshalByRefObjectをは別のAppDomain内または、例えばTCP/IPを介して、他のプロセスまたは別のコンピュータで呼び出すことができるので、コンパイラは、あなたに警告を与えるこのような理由のために、メソッドとプロパティでのみ動作します。

+1

MarshapByReferenceについてのあなたのコメントをちょっと詳しく説明できますか?私はそれをかなり理解しておらず、したいと思います。役に立つ情報をありがとう。 –

+1

自動プロパティは、フレームワークではなくコンパイラと関係しています。古いフレームワークをターゲットにして、最新のコンパイラで自動プロパティを使用することができます。 –

+0

はい、ありがとう:)修正済みです。 –

0

個人的には、私はこのように考えています。後で、「コンテナ」が決してnullではないという不確定性を確立したいとしましょう。パブリックフィールドとして定義されている場合、これを実行する方法は、それを使用するすべてのクライアントを検索し、nullに設定されないようにするコードを入れることです。私はプロパティとしてそれを持っている場合は、同じようなものを用いて達成することができます。

private static IUnityContainer _container = new ContainerImpl(); 
public static IUnityContainer Container 
{ 
    get 
    { 
     return _container; 
    } 
    set 
    { 
     _container = value ?? _container; 
    } 
} 

それとも、あなたはより表現であることをNULL値に例外を投げることができました。詳細は重要ではありませんが、カプセル化の角度は重要です。

私はそれが単純な反応ではなく、特に静的なキーワードに直面している現実的で合理的なものだと考えています。カプセル化がなければ、それは文字どおり大域変数です。少なくともグローバルな状態をカプセル化することで、アプリケーション全体のコントロールを漏らしたり、クライアントの信頼性を維持したりすることなく、プロバイダーが制御できるようになります。

「自分を繰り返さないでください」の問題として考えるかもしれません。フィールドに来るときの共通のロジックは、必然的にその場全体に複製されます。

+0

もしあなたがフィールドや自動プロパティを持っているのであれば、副作用のないコードを自由に変更することができます。もちろん、関数によってはフィールドbyrefを渡そうとします。 –

関連する問題