1

わかりました、これは実際の要件よりも好奇心です。

私がこのクラスを持っているとしましょう:

public sealed class Entity
{
    int value;

    Entity()
    {

    }

    public static implicit operator Entity(int x)
    {
        return new Entity { value = x };
    }
}

このクラスがクラスの外でインスタンス化されることを望まないので、これは機能します。ただし、ここではEntitysが参照され、値型のようにコピーされません。このクラスは非常に小さいので、値型のように動作させたいと思います。Entityまた、 sの2つのインスタンスを比較するe1 == e2と、参照が等しくなります(オーバーロードすることはできます==が、それはより多くの作業です)。だから私はそれを構造体にします:

public struct Entity
{
    int value;

    public static implicit operator Entity(int x)
    {
        return new Entity { value = x };
    }
}

しかし今、誰かがnew Entity()簡単にできるようになりました。

私の質問は、タイプ(構造体/クラス)を持つことができる方法があります

1)値にアクセスするたびにコピーされるため、

Entity e1 = 1;
Entity e2 = e1;
ReferenceEquals(e1, e2); // prints false, just like any value type

2)同等性を比較するときに値のセマンティクスがあります

Entity e1 = 1;
Entity e2 = 1;
e1.Equals(e2); // prints true

// this is easy though by overriding default equality.

3)次のタイプの範囲外ではインスタンス化できません。

Entity e = new Entity(); // should not compile

基本的に列挙型の動作に近いです。私は確かにそれなしで生きることができます、ただ学ぶだけです。

4

3 に答える 3

2

C#コンパイラは、パラメータなしのコンストラクタが何もしないという仮定に基づいてコードを定期的にコンパイルするため、C#の構造体のデフォルトコンストラクタを再定義したり非表示にしたりすることはできません。.NETで構造体のデフォルトコンストラクタを定義できないのはなぜですか?を参照してください。。

あなたのオプションはどちらかです

  • クラスを使用する
  • 構造体のデフォルト値に何らかの意味があることを確認してください(たとえば、あなたの場合、intは0に初期化されます)-これは列挙型が行うことです(列挙型は0に初期化されることを思い出してください)。

パフォーマンスの問題があることがわかるまで、クラスを使用することをお勧めします。

于 2013-02-19T15:14:40.020 に答える
1

タイプは、そのタイプのストレージの場所に何が起こるかについて何も言いません。任意のタイプのストレージ ロケーションが存在するようになるか、そのコンテンツが同じタイプの他のロケーションのコンテンツで上書きされる可能性があります。タイプ自体が問題に関与することはありません。参照型の格納場所には、クラス参照が保持されます。存在するようになると、null 参照になります。参照型の格納場所が null 参照以外のものを保持する唯一の方法は、その型のインスタンスが作成され、完全信頼コードとリフレクションを含むいくつかのシナリオ以外では、参照型がその参照を完全に制御できる場合です。それが起こりうる状況。

対照的に、値型の格納場所はその型のインスタンスです。したがって、構造がどのように存在するかを制御できる方法はありません。構造体が (限られた範囲で) 制御できるのは、そのフィールドに含めることができる値です。信頼が制限されたシナリオでは、構造体のコードがその値を構造体のインスタンスに書き込む場合にのみ、プライベート構造体フィールドはデフォルト以外の値を想定できます (値が構造体の任意のインスタンスに書き込まれる場合、信頼が制限されたコードであっても)そのインスタンスへのアクセス権を持つユーザーは、マルチスレッドのオーバーラップ読み取りと書き込みを使用して、構造体自体が作成することのないフィールド値の組み合わせを持つ構造体を生成できる場合があります)。

クラス型の単一のプライベート フィールドを持つ構造体を作成することをお勧めします。コードが を作成するのを防ぐことはできませんdefault(Entity)が、それは、コードが何か有用なことを実行できるようにする必要があるという意味ではありません。そのメソッドは、別の既定のインスタンスと比較した場合、および他のものと比較した場合にEquals十分に機能し、すべての既定のインスタンスに対して同じ値を返す必要がありますが、他のメソッドは例外をスローする可能性があります。truefalseGetHashCode

于 2013-02-19T16:03:57.070 に答える
-1

classのすべてのコンストラクター (静的コンストラクターを除く)privateを作成します。も機能しますが、そのため、あまり意味がありません。 Entityprotectedsealed

于 2013-02-19T15:00:26.873 に答える