2012-09-24 31 views
72

C#では、基本クラスオブジェクトを派生クラスの1つに明示的に変換できますか?私は、基本クラスオブジェクトをパラメータとして受け取り、プロパティ値をコピーする派生クラスのコンストラクタを作成する必要があると考えています。私はこの考えが本当に好きではないので、可能ならば避けたい。基底クラスを派生クラスに変換

それが動作するはずのようにこれが(オブジェクトは、新たな拠点としてインスタンス化されるので、メモリは、派生クラスの余分なメンバーのために割り当てられるべきではない)が、C#は、私はそれを行うことができるように思わいないようです:

class BaseClass 
{ 
    ... some stuff ... 
} 

class DerivedClass : BaseClass 
{ 
    public bool MyDerivedProperty{ get; set; } 
} 


static void Main(string[] args) 
{ 
    BaseClass myBaseObject = new BaseClass(); 
    DerivedClass myDerivedObject = myBaseObject as DerivedClass; 

    myDerivedObject.MyDerivedProperty = true; 
} 
+4

あなたは最後の行にはnull参照の例外を取得するつもりです。 – Erix

+0

すでに回答済み:http://stackoverflow.com/questions/729527/is-it-possible-to-assign-a-base-class-object-to-a-derived-class-reference-with-a –

+1

あなた通常のキャストと対比して "as"を使用するのが適切である時について読むべきです。ここでキャストを使うと、C#コンパイラはあなたがしていることが間違っているとあなたに伝えます。 –

答えて

57

いいえ、あなたが言うようにクラスを変換する組み込みの方法はありません。これを行う最も簡単な方法は、提案したことをすることです:DerivedClass(BaseClass)コンストラクタを作成します。他のオプションは基本的に、ベースから派生したインスタンスへのプロパティのコピーを自動化するために出てくるでしょう。反射を使ってあなたがasを使用して掲載

コードは、私はあなたが見てきた確信しているとして、コンパイルされますが、あなたがそれを実行したときに、それはDerivedClassのインスタンスではありませんので、myBaseObject as DerivedClassは、nullに評価されるため、null参照の例外がスローされます。

1

いいえ、このための変換は組み込まれていません。 前述のようなコンストラクタやその他の変換メソッドを作成する必要があります。

また、BaseClassはDerivedClassではないため、myDerivedObjectはnullになり、上の最後の行はnull ref例外をスローします。

3

不可能です。可能な唯一の方法は、

static void Main(string[] args) 
{ 
    BaseClass myBaseObject = new DerivedClass(); 
    DerivedClass myDerivedObject = myBaseObject as DerivedClass; 

    myDerivedObject.MyDerivedProperty = true; 
} 
+5

これはNullReferenceExceptionをスローしますので、このように動作しません –

+0

他の回答はキャストする方法を教えていません –

+0

時には少し再考すると、大きな問題から救うことができます。ありがとうございました! – peter70

5

です。自分で変換を実装することはできますが、お勧めしません。既存のオブジェクトの機能を拡張するためにこれを行う場合は、Decorator Patternを見てください。

33

これはできません。しかし、あなたはAutoMapper

例のように、オブジェクトマッパーを使用することができます。

Global.asaxのか、アプリケーションの起動時に
class A 
{ 
    public int IntProp { get; set; } 
} 
class B 
{ 
    public int IntProp { get; set; } 
    public string StrProp { get; set; } 
} 

AutoMapper.Mapper.CreateMap<A, B>(); 

使用法:

var b = AutoMapper.Mapper.Map<B>(a); 

それは経由して簡単に設定です流暢なAPIです

7

私はこれに1つの解決策を見つけましたが、それは最高のものではありませんが、私にはきれいに感じられ、コードに大きな変更を加える必要はありません。私のコードはあなたのものと似ていました。

私の基本クラス

public class MyBaseClass 
{ 
    public string BaseProperty1 { get; set; } 
    public string BaseProperty2 { get; set; } 
    public string BaseProperty3 { get; set; } 
    public string BaseProperty4 { get; set; } 
    public string BaseProperty5 { get; set; } 
} 

私の派生クラス

public class MyDerivedClass : MyBaseClass 
{ 
    public string DerivedProperty1 { get; set; } 
    public string DerivedProperty2 { get; set; } 
    public string DerivedProperty3 { get; set; } 
} 

public MyBaseClass GetPopulatedBaseClass() 
{ 
    var myBaseClass = new MyBaseClass(); 

    myBaseClass.BaseProperty1 = "Something" 
    myBaseClass.BaseProperty2 = "Something else" 
    myBaseClass.BaseProperty3 = "Something more" 
    //etc... 

    return myBaseClass; 
} 
人口ベースクラスを取得する前の方法3210

私は私にエラー

public MyDerivedClass GetPopulatedDerivedClass() 
{ 
    var newDerivedClass = (MyDerivedClass)GetPopulatedBaseClass(); 

    newDerivedClass.UniqueProperty1 = "Some One"; 
    newDerivedClass.UniqueProperty2 = "Some Thing"; 
    newDerivedClass.UniqueProperty3 = "Some Thing Else"; 

    return newDerivedClass; 
} 

をキャストすることができないを与えたこのことを、しようとしていた前に、怒鳴る、次のように私は私のコードを変更し、動作しているようですし、今より理にかなって:

public MyBaseClass GetPopulatedBaseClass() 
{ 
    var myBaseClass = new MyBaseClass(); 

    myBaseClass.BaseProperty1 = "Something" 
    myBaseClass.BaseProperty2 = "Something else" 
    myBaseClass.BaseProperty3 = "Something more" 
    //etc... 

    return myBaseClass; 
} 

public void FillBaseClass(MyBaseClass myBaseClass) 
{ 
    myBaseClass.BaseProperty1 = "Something" 
    myBaseClass.BaseProperty2 = "Something else" 
    myBaseClass.BaseProperty3 = "Something more" 
    //etc... 
} 

public MyDerivedClass GetPopulatedDerivedClass() 
{ 
    var newDerivedClass = (MyDerivedClass)GetPopulatedBaseClass(); 

    newDerivedClass.UniqueProperty1 = "Some One"; 
    newDerivedClass.UniqueProperty2 = "Some Thing"; 
    newDerivedClass.UniqueProperty3 = "Some Thing Else"; 

    return newDerivedClass; 
} 

public MyDerivedClass GetPopulatedDerivedClass() 
{ 
    var newDerivedClass = new MyDerivedClass(); 

    FillBaseClass(newDerivedClass); 

    newDerivedClass.UniqueProperty1 = "Some One"; 
    newDerivedClass.UniqueProperty2 = "Some Thing"; 
    newDerivedClass.UniqueProperty3 = "Some Thing Else"; 

    return newDerivedClass; 
} 
+0

非常に良い!まさに私が欲しい! thx:D –

+4

プロパティを追加するたびにこれを編集する必要があります。他の人にはこれを読んでも構わないと思います –

関連する問題