2016-07-07 3 views
0

Я имею вопрос, и, вероятно, это не может быть сделано таким образом, но может быть, есть какой-то другой способ, я не знаю, так что у меня есть класс, который выглядит следующим образом:C# класс перезапись возможность

[DataContract] 
    public class Parent 
    { 
     [DataMember(Name="id")] 
     public int Id { get; set; } 
     [DataMember(Name = "value")] 
     public int Value { get; set; } 
    } 

Теперь этот класс является значение атрибута другого класса:

[DataContract] 
    public class Location 
    { 
     [DataMember(Name="parent")] 
     public Parent Parent { get; set; } 
    } 

Но есть улов, мне нужны отдельные классы кругооборота же типа, например:

[DataContract] 
    public class Parent 
    { 
     [DataMember(Name="id")] 
     public int Id { get; set; } 
    } 

    [DataContract] 
    public class Parent 
    { 
     [DataMember(Name = "value")] 
     public int Value { get; set; } 
    } 

В зависимости от значения null или нет (и мне нужно, чтобы это было причиной отдельного объекта, поскольку вы видите, что я хочу его сопоставить). Можно ли перезаписать класс, чтобы один класс мог иметь только один или другой атрибут?

+3

Что касается создания контрактов идет ... не было бы достаточно иметь один класс «Parent» с свойствами BOTH, но пометить эти свойства как ** nullable **? – Shaamaan

+1

Если оба класса представляют разные вещи (что они делают, поскольку они имеют совершенно разные члены), они также должны иметь разные имена. Нет способа (и нет причин) использовать одно и то же имя для разных классов, если они находятся в одном и том же пространстве имен. – HimBromBeere

ответ

1

Вы могли бы решить с наследованием, но ИМХО он получает запасом прочности.

Лично я бы все положил в класс Родитель. Сделайте свойства обнуляемыми, чем это сделано. Если вы хотите иметь некоторую надежность, если установлено хотя бы одно свойство, вы можете сделать частные сеттеры (учитывая, что вам не нужно их изменять после создания родителя) и иметь фабричные методы для создания родителей с идентификатором или ценность.

Родитель с инкапсуляцией (если требуется):

[DataContract] 
public class Parent 
{ 
    private Parent() {} 

    [DataMember(Name="id")] 
    public int? Id { get; private set; } 

    [DataMember(Name = "value")] 
    public int? Value { get; private set; } 

    public static Parent CreateWithId(int id) 
    { 
     return new Parent { Id = id }; 
    } 

    public static Parent CreateWithValue(int value) 
    { 
     return new Parent { Value = value }; 
    } 
} 

Вы можете дополнительно добавить свойство ParentType который возвращает значение перечисления, которое либо ParentType.ValueParent или ParentType.IdParent. Опять же, это полезно только тогда, когда это необходимо, например. потому что это упрощает обращение с родителями, когда есть возможность получить более разные типы или когда вы захотите поддержать Id Parents с нулевым значением как Id или то же самое со значением.


Совершенно другое решение - хранить как Id, так и Value в том же свойстве, поскольку оба являются целыми числами. Иметь другой способ отличить его от Идентификатора или значения.

[DataContract] 
public class Parent 
{ 
    [DataMember(Name="id")] 
    public int Data { get; private set; } 

    [DataMember(Name="id")] 
    public ParentType ParentType { get; private set; } 

    public static Parent CreateWithId(int id) 
    { 
     return new Parent { Data = id, ParentType = ParentType.Id }; 
    } 

    public static Parent CreateWithValue(int value) 
    { 
     return new Parent { Data = value, ParentType = ParentType.Value }; 
    }   
} 
0

Вы пытаетесь представить РАЗНЫЕ данные, создавая два разных класса, которые называются одинаковыми. Это ошибка. Первоначально я хотел предложить использовать интерфейсы или наследование, но это не имеет смысла, поскольку оба класса, которые вы написали, содержат разные вещи, и нет совпадений.

Если этот случай направлен исключительно потому, что вам необходимо сопоставить эти свойства с некоторыми контрактами на данные, то почему бы не использовать класс Parent с обоими свойствами и просто сделать эти свойства Nullable?

Что-то вдоль линий:

[DataContract] 
public class Parent 
{ 
    [DataMember(Name="id")] 
    public int? Id { get; set; } 

    [DataMember(Name = "value")] 
    public int? Value { get; set; } 
} 
0

1 Как сказано в HimBromBree, вы можете поместить классы родителя в разные пространства имен.

WCF также позволяет предоставлять различные имена для сериализации классов через [DataContract] атрибута:

[DataContract(Name="ParentA")] 
public class Parent { 
    [DataMember(Name="id")] 
    public int Id { get; set; } 
} 

2 Если ваша цель иметь класс Parent для хранения различных значений (Value или Id), в зависимости от обстоятельств, вы также может создавать два родительских класса родителя.

Давайте называть эти классы ParentA и ParentB

Тогда на Родитель, вы должны сделать заявление для полиморфного серийности:

[DataContract] 
[KnownType(typeof(ParentA))] 
[KnownType(typeof(ParentB))] 
public class Parent {} 


[DataContract(Name="ParentA")] 
public class ParentA : Parent { 
    [DataMember(Name="id")] 
    public int Id { get; set; } 
} 
Смежные вопросы