Копирование свойства интерфейса в С#
Я работаю с С# уже много лет, но просто сталкиваюсь с этой проблемой, которая меня бросает, и я действительно даже не знаю, как задать вопрос, поэтому на примере!
public interface IAddress
{
string Address1 { get; set; }
string Address2 { get; set; }
string City { get; set; }
...
}
public class Home : IAddress
{
// IAddress members
}
public class Work : IAddress
{
// IAddress members
}
Мой вопрос: я хочу скопировать значение свойств IAddress из одного класса в другой. Возможно ли это в простом однострочном выражении или мне все еще нужно назначить свойство-собственность каждому из них? Я на самом деле очень удивлен, что эта, казалось бы, простая вещь заставила меня замолчать, как будто она... Если это не представляется возможным в краткой форме, есть ли у кого-нибудь какие-либо ярлыки, которые они используют, чтобы делать такие вещи?
Спасибо!
Ответы
Ответ 1
Для этого нет ни одного лайнера.
Если вы сделаете это много, вы можете посмотреть на какую-то форму генерации кода, возможно, используя шаблоны T4 и Reflection.
У BTW COBOL есть выражение для этого: ПЕРЕМЕЩЕНИЕ КОРРЕСПОНДЕНА ДОМА ДЛЯ РАБОТЫ.
Ответ 2
Здесь один из способов сделать это, который не имеет ничего общего с интерфейсами:
public static class ExtensionMethods
{
public static void CopyPropertiesTo<T>(this T source, T dest)
{
var plist = from prop in typeof(T).GetProperties() where prop.CanRead && prop.CanWrite select prop;
foreach (PropertyInfo prop in plist)
{
prop.SetValue(dest, prop.GetValue(source, null), null);
}
}
}
class Foo
{
public int Age { get; set; }
public float Weight { get; set; }
public string Name { get; set; }
public override string ToString()
{
return string.Format("Name {0}, Age {1}, Weight {2}", Name, Age, Weight);
}
}
static void Main(string[] args)
{
Foo a = new Foo();
a.Age = 10;
a.Weight = 20.3f;
a.Name = "Ralph";
Foo b = new Foo();
a.CopyPropertiesTo<Foo>(b);
Console.WriteLine(b);
}
В вашем случае, если вам нужен только один набор свойств интерфейса для копирования, вы можете сделать это:
((IAddress)home).CopyTo<IAddress>(b);
Ответ 3
Вы можете создать метод расширения:
public static void CopyAddress(this IAddress source, IAddress destination)
{
if (source is null) throw new ArgumentNullException("source");
if (destination is null) throw new ArgumentNullException("destination");
//copy members:
destination.Address1 = source.Address1;
//...
}
Ответ 4
Jimmy Bogard AutoMapper очень полезен для такой операции отображения.
Ответ 5
Я не верю, что для этого есть готовое к языку решение (все свойства должны иметь геттеры и сеттеры).
Вы можете создать Address как абстрактный класс с помощью метода Copy (Address add).
В качестве альтернативы вы можете сделать Home и Work, чтобы иметь IAddress, и не расширять его. Затем копия будет немедленной.
Ответ 6
Вам нужно будет создать метод для этого
public void CopyFrom(IAddress source)
{
this.Address1 = source.Address1;
this.Address2 = source.Address2;
this.City = source.city;
}
Ответ 7
У вас может быть конструктор для каждого класса с помощью IAddress и внедрены члены, заполненные внутри.
например,
public WorkAddress(Iaddress address)
{
Line1 = IAddress.Line1;
...
}
Для удобства использования используйте отражение, чтобы получить имена свойств.
НТН,
Dan
Ответ 8
Если вы инкапсулируете общие части дома и рабочий адрес в отдельный класс, это может сделать вашу жизнь проще. Затем вы можете просто скопировать это свойство. Мне кажется, что это лучший дизайн.
В качестве альтернативы вы можете взломать решение с отражением и атрибутами, где значение свойств в одном объекте копируется в соответствующие (и отмеченные) свойства в другом. Конечно, это не будет однострочное решение, но оно может быть быстрее и удобнее, чем другие, если у вас есть большой набор свойств.