Список как копия списка родительского класса

Qwe.Qwe1

Как можно создать список элементов как копию списка родительского класса?
Я так понимаю можно с помощью Select перечислять все поля и прочее, а есть ли способ проще? Cast? OfType? ConvertAll?

namespace ConsoleApplication1
{
 class Program
 {
 static void Main(string[] args)
 {
 List<Animal> animals = new List<Animal>()
 {
 new Animal() { Name = "One", Age = 1 },
 new Animal() { Name = "Two", Age = 2 },
 new Animal() { Name = "Three", Age = 3 }
 };

 List<Cat> cats = ???
 }
 }

 public class Animal
 {
 public string Name { get; set; }
 public int Age { get; set; }
 }

 public class Cat : Animal
 {
 public string Color { get; set; }
 }
}
19 ответов

Qwe.Qwe1

Cast.Но смысл?????


Qwe.Qwe1

Cast у меня Exception выдает... OfType без ошибок, но список пустой.Зачем? Есть готовый список значений, нужен второй такой же, но с дополнительным полем.


Qwe.Qwe1

Ну то есть можно ли как-то обойтись без перечисления полей родительского класса:
List<Cat> cats = animals.Select(x => new Cat() { Name = x.Name, Age = x.Age, Color = null }).ToList();
Чтобы не завязываться на них..


Qwe.Qwe1

Cast у меня Exception выдает... OfType без ошибок, но список пустой.
упс, неверно прочитал задачу. Естественно, OfType выдает пустоту, потому что нет Cat-ов, их нужно создавать принудительно.


Qwe.Qwe1

У тебя в зверинце 3 зверя, но кошек среди них нетИменно по-этому:
Cast у меня Exception выдает... OfType без ошибок, но список пустой.


Qwe.Qwe1

Так в итоге как быть? )


Qwe.Qwe1

Так в итоге как быть? )
Писать велосипед с рефлексией. Прикрутить (Auto|...)Mapper?


Qwe.Qwe1

Ну то есть можно ли как-то обойтись без перечисления полей родительского класса:
List<Cat> cats = animals.Select(x => new Cat() { Name = x.Name, Age = x.Age, Color = null }).ToList();
Чтобы не завязываться на них..
Сделать конструктор и передать в него другой объект. Но не знаю, тут будет ли работать.


Qwe.Qwe1

Cast у меня Exception выдает... OfType без ошибок, но список пустой.Зачем? Есть готовый список значений, нужен второй такой же, но с дополнительным полем.
Как только Вы объясните, как из слона сделать кота, мы легко найдем решение.Пока слон в кошачью клетку у меня не влезает)А вообще учим ООП:Из базового класса невозможно получить наследника. Никак. Только конструктор, только хардкор.Как вариант можно написать explicit конвертацию, но это все равно будет синтаксический сахар.


Qwe.Qwe1

Сделать конструктор и передать в него другой объект. Но не знаю, тут будет ли работать.
Само по себе не будет. Если есть метод вроде Copy, то можно через него.


Qwe.Qwe1

вроде Copy,
Да. Или типа Obj.AssignКакая то фабрика классов или Строитель.Если Linq не дружит, то ручной маппинг неизбежен. Что тут плохого.


Qwe.Qwe1

ICloneable.Clone()


Qwe.Qwe1

Ну ладно, раз уж пошла такая пьянка в пятницу: ))Еще reflection, emit, сериализация - десериализация?Extention к классу/object, explicit к преобразованию, extention к List?Кто больше? )PS Что только люди не сделают, лишь бы не работать, свойства им лень копировать ;)


Qwe.Qwe1

PS Что только люди не сделают, лишь бы не работать, свойства им лень копировать ;)
))


Qwe.Qwe1

Ну ладно, раз уж пошла такая пьянка в пятницу: ))Еще reflection, emit, сериализация - десериализация?Extention к классу/object, explicit к преобразованию, extention к List?Кто больше? )
Сериализация в XML, через XSLT добавить нужное поле, через XPATH собрать ноды этого поля, заполнить их нужными значениями, обратно десериализовать из XML в нужный тип )


Qwe.Qwe1

Сделать конструктор и передать в него другой объект. Но не знаю, тут будет ли работать.
class Program
	{
		static void Main(string[] args)
		{
			var _animals = new List<Animal>()
			{
				new Animal() { Name = "One", Age = 1 },
				new Animal() { Name = "Two", Age = 2 },
				new Animal() { Name = "Three", Age = 3}
			};

			var _cats = _animals.Select(x => new Cat(x).ToString()).ToArray();
			Console.WriteLine(String.Join("\n", _cats));
			Console.ReadLine();
		}
	}

	public class Animal
	{
		public string Name { get; set; }
		public int Age { get; set; }
	}

	public class Cat : Animal
	{
		public Cat(Animal a)
		{
			this.Name = a.Name;
			this.Age = a.Age;
			this.Color = "Полосатый";
		}

		public string Color { get; set; }

		public override string ToString()
		{
			return String.Format(
				"Name - {0}, Age - {1}, Color - {2}", this.Name, this.Age, this.Color);
		}
	}


Qwe.Qwe1

[quot Addx]
Как вариант можно написать explicit конвертацию, но это все равно будет синтаксический сахар.
public class Animal
	{
		public string Name { get; set; }
		public int Age { get; set; }

		public static explicit operator Cat(Animal a)
		{
			return new Cat() { Name = a.Name, Age = a.Age, Color = "В полоску" };
		}
	}

	public class Cat : Animal
	{
		public string Color { get; set; }

		public override string ToString()
		{
			return String.Format(
				"Name - {0}, Age - {1}, Color - {2}", this.Name, this.Age, this.Color);
		}
	}
Ошибка компиляции
Animal.explicit operator Cat(Animal)': user-defined conversions to or from a derived class are not allowed


Qwe.Qwe1

зачем городить всю эту ахинею, если объект не поддерживает интерфейс клонирования, то его нельзя клонировать. Точка. Если поддерживает, значит можно. Вот такое "клонирование" может иметь тяжелые последствия, когда часть объекта будет доступа из 2 разных клонов


Qwe.Qwe1

[quot .NET]
пропущено...Ошибка компиляциипропущено...
Да, тупанул, спасибо. Обойдемся без этого сахара. )