2015-03-23 2 views
2

У меня возникают некоторые проблемы с установочным отношением между двумя классами. У меня есть 2 классов, студент:Как установить правильное отношение между двумя классами

class Student { 
    String name 
    Guardian father 
    Guardian mother 
    Guardian local_guardian 
} 

и Guardian:

class Guardian { 
    String name; 
    static hasMany = [children:Student] 
    static mappedBy = [children:'father'] 
} 

Здесь я использовал mappedBy для отображения объекта Гардиан отцу собственности. Если mappedBy, я получал сообщение об ошибке, должен использовать mappedBy с любым из трех свойств класса Student. Я попробовал этот запрос, чтобы ввести некоторые выборочные данные

new Student(name:"John", father: new Guardian(name:"Michael").save(), 
      mother: new Guardian(name:"Mary").save(), 
      local_guardian: new Guardian(name:"James").save()).save(flush:true); 

Данные получать успешно сохранен, но моя проблема, так как я использовал mappedBy со свойством «отца», я могу использовать Guardian.children только с этим отцом объект. , когда я пытаюсь получить список детей с объектами mother и local_guardian, (напр .: mother.children) получает нулевой результат. Я попытался, добавив с AddTo на многих сторонах как

Guardian.findByName("Mary").addToChildren(
    Student.findByName("John")).save(flush:true); 

и попытался доступ

Guardian.findByName("Mary").children 

Здесь я получил результат, но он переехал ребенок от отца к матери объекту, и больше не доступ к father.children Как я могу решить этот сценарий? То, что я пытаюсь достичь, я должен иметь возможность получить список детей из всех трех объектов Guardian. Здесь один объект Student указывает на 3 объекта Guardian (отец, мать, local_guardian). Так что я должен быть в состоянии получить список детей,

  1. father.children
  2. mother.children
  3. local_guard.children

Как я правильно установить соотношение между этими классами в решить мою проблему?

ответ

1

Если вы хотите реализовать это отношение, используя hasMany, тогда вам нужно будет иметь три сопоставленных класса Guardian.

static hasMany = [children:Student, motherChildres:Student, localGuardianChildrens:Student] 
    static mappedBy = [children:'father', motherChildrens:'mother', localGuardianChildrens: 'local_guardian'] 

Но это не выглядит хорошо, вместо этого вы можете осуществлять связь, используя класс домена среднего уровня и добавить addToChildren и getChildrens методы в классе Хранителя, как показано ниже.

class GuardianChildren { 
    Guardian guardian 
    Student student 

    constraints { 
    student unique: ['guardian'] 
    } 

} 

Guardian { 
    void addToChildrens(Student child) { 
     new GuardianChildren(guardian:this, student:child).save() 
    } 

    @Transient 
    List<Student> getChildrens() { 
     return GuardianChildren.findAllByGuardian(this).children 
    } 
} 

Student { 

    @Transient 
    Guardian getMother() { 
    //find guardin children where guardian type is mother and children is this student 
    } 

    @Transient 
    Guardian getFather() {..} 
} 

Удалить hasMany из Guardian и отчество/мать от Студента. Вам также, вероятно, понадобится поле типа в Guardian, чтобы указать, является ли это матерью/отцом и т. Д.

+0

Я пробовал это, почти получил работу, но когда я пытаюсь вызвать 'addToChildrens' на объект Guardian, я получаю сообщение об ошибке 'Нет подписи метода: java.util.ArrayList.addToChildrens() применим для типов аргументов: (studenttest.Student) значения: [studenttest.Student: 1]' – dev

+0

проверить объект, на который вы вызываете метод addToChildrens, его не объект-хранитель, но ArrayList. не используйте def, используйте реальные типы для объявления переменных, и вы увидите, что пойдет не так. –

+0

Отлично! Я получил его работу. Я использовал 'findAllBy', который возвращает' List'. Теперь он изменился на 'findBy' и начал работать. Но есть еще одна проблема. Мне пришлось использовать 'def addToChildrens (Student child)' вместо 'void addToChildrens (Student child)'. когда я использую void, получая ошибку компиляции. Какая может быть причина? – dev

0

Возможно, вы захотите использовать hasMany и belongsTo, а затем, чтобы определить опекуна, вы можете использовать что-то вроде свойства отца, матери, localGuardian в объекте опекуна. С такими отношениями вы можете использовать transients для определения набора детей и матери/отца.

Так, например

class Student 
    { 
     String name 
     Guardian local_guardian 
     static belongsTo = [primaryGuardian: Guardian] 
     static transients=['mother', 'father'] 
     //define the transients 
     def getMother(){ 
      if(primaryGuardian.type == 'mother') { 
       return primaryGuardian 
      } else { 
      return primaryGuardian.spouse 
      } 
     } 
     //do something similiar for getFather 
     } 

    Class Guardian 
     { 
     String name 
     String type 
     Guardian spouse 
     static hasMany = [children:Student, localGuardianStudents: Student] 
     }  

Пожалуйста, обратите внимание, что это только пример кода, и может содержать ошибки, я не проверял.
Таким образом, вы можете создать опекун, а затем добавить ребенок по телефону

guardian.addToChildren(child) 

В любом случае, это позволит вам получить ребенок опекуна по телефону guardian.children, это позволяет получить первичный опекун (или мать или отца) ребенка, позвонив по номеру child.primaryGuardian, и он позволяет получить мать или отца, позвонив по телефону child.mother без необходимости добавлять туда специальные типы.

Вы должны убедиться, что вы изменяете ограничения здесь, чтобы супруг мог быть пустым.Кроме того, отношения такого рода могут иногда становиться сложными при создании их, вызывающих ошибки, связанные с отсутствующими идентификационными номерами, когда вы пытаетесь сохранить, поэтому вы должны быть уверены, что убедитесь, что обе стороны отношения определены при создании и изменении этих объекты.

Смежные вопросы