Добавление коллекции, петля нужна? - PullRequest
1 голос
/ 01 декабря 2009

У меня есть этот код:

Schedule s = _entities.Schedules.Where(x => x.ScheduleID == schedule.ScheduleID && x.BookingObject.BookingObjectID == bookingObjectID).FirstOrDefault();

if(s == null)
    s = new Schedule();

s.ScheduleStart = schedule.ScheduleStart;
s.ScheduleEnd = schedule.ScheduleEnd;

foreach (var t in schedule.Timetables)
{   
    s.Timetables.Add(t);
}

_entities.AddToSchedules(s);

_entities.SaveChanges();

Исключение: System.InvalidOperationException

расписание объекта передается в качестве параметра

EDIT:

изменено на:

  Schedule sh = new Schedule();


  sh.ScheduleStart = schedule.ScheduleStart;
  sh.ScheduleEnd = schedule.ScheduleEnd;

  foreach (var t in schedule.Timetables)
  {
       //sh.Timetables.Add(t);  // doesn't work
        sh.Timetables.Add(new Timetable { DayOfWeek = t.DayOfWeek, StartTime = t.StartTime, EndTime = t.EndTime });   // works
  }

  _entities.AddToSchedules(sh);

  _entities.SaveChanges();

Есть ли логическая причина, по которой sh.Timetables.Add (t) не работает, поскольку это коллекция Timetable?

/ М

Ответы [ 5 ]

2 голосов
/ 01 декабря 2009
foreach(var time in schedule.Timetables){
     s.Timetables.Add(time)
}

Вы можете перебирать временные таблицы в schedule.Timetables и добавлять их в новую сущность.

1 голос
/ 01 декабря 2009

ОБНОВЛЕНИЕ: Только что подтвердил, что это может быть причиной. И создал новый совет в моей серии советов для объяснения.

Я могу вспомнить одну возможную причину. Есть ли связь между schedule.Timetables один ко многим? То есть Можно ли назначить расписание только одному расписанию за раз?

Если это так, то это невозможно:

  foreach (var t in schedule.Timetables)  {       
     sh.Timetables.Add(t); 
  }

Потому что, когда вы добавляете 't' в другое расписание, оно автоматически удаляется из старой коллекции schedule.Timetables, что, конечно, изменяет перечисляемую коллекцию, то есть нет-нет.

Если это так, решение состоит в том, чтобы просто сделать что-то вроде этого:

  var timetables = schedule.Timetables.ToArray();
  foreach (var t in timetables)  {       
     sh.Timetables.Add(t); 
  }

Здесь вы перечисляете коллекцию до того, как начнете ее изменять.

1 голос
/ 01 декабря 2009

Посмотрите на первые несколько строк:

Schedule s = _entities.Schedules.Where(x => x.ScheduleID == schedule.ScheduleID && x.BookingObject.BookingObjectID == bookingObjectID).FirstOrDefault();

if(s == null)
    s = new Schedule();

В первой строке вы запрашиваете базу данных для объекта с тем же ScheduleID, что и schedule, и сохраняете возвращенную ссылку в s. Предполагая, что объект доступен в базе данных, вы фактически указываете s на тот же объект, что и schedule. Это означает, что s.Timetables и schedule.Timetables - это одна и та же коллекция, что приведет к исключению, которое вы получите во время foreach.

Я предполагаю, что вы хотите клонировать только объект, на который указывает расписание, и вставить его в базу данных , если его еще нет в базе данных . В этом случае:

Schedule s = _entities.Schedules.Where(x => x.ScheduleID == schedule.ScheduleID && x.BookingObject.BookingObjectID == bookingObjectID).FirstOrDefault();

if(s == null)
{
    s = new Schedule();

    s.ScheduleStart = schedule.ScheduleStart;
    s.ScheduleEnd = schedule.ScheduleEnd;

    foreach (var t in schedule.Timetables)
    {   
        s.Timetables.Add(t);
    }

    _entities.AddToSchedules(s);

    _entities.SaveChanges();
}
1 голос
/ 01 декабря 2009

Другой вариант будет:

((List<TimeTable>)s.Timetables).AddRange(((List<TimeTable>)schedule.Timetables));
1 голос
/ 01 декабря 2009
s.Timetables.Add(schedule.Timetables)

если это не так, скорее всего, ваш вопрос нуждается в дополнительной информации. Что такое s.Timetables, schedule.Timetables? (типы)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...