How does this code break the Law of Demeter?
        Posted  
        
            by Dave Jarvis
        on Stack Overflow
        
        See other posts from Stack Overflow
        
            or by Dave Jarvis
        
        
        
        Published on 2010-04-09T16:43:18Z
        Indexed on 
            2010/04/09
            16:53 UTC
        
        
        Read the original article
        Hit count: 419
        
The following code breaks the Law of Demeter:
public class Student extends Person {
  private Grades grades;
  public Student() {
  }
  /** Must never return null; throw an appropriately named exception, instead. */
  private synchronized Grades getGrades() throws GradesException {
    if( this.grades == null ) {
      this.grades = createGrades();
    }
    return this.grades;
  }
  /** Create a new instance of grades for this student. */
  protected Grades createGrades() throws GradesException {
    // Reads the grades from the database, if needed.
    //
    return new Grades();
  }
  /** Answers if this student was graded by a teacher with the given name. */
  public boolean isTeacher( int year, String name ) throws GradesException, TeacherException {
    // The method only knows about Teacher instances.
    //
    return getTeacher( year ).nameEquals( name );
  }
  private Grades getGradesForYear( int year ) throws GradesException {
    // The method only knows about Grades instances.
    //
    return getGrades().getForYear( year );
  }
  private Teacher getTeacher( int year ) throws GradesException, TeacherException {
    // This method knows about Grades and Teacher instances. A mistake?
    //
    return getGradesForYear( year ).getTeacher();
  }
}
public class Teacher extends Person {
  public Teacher() {
  }
  /**
   * This method will take into consideration first name,
   * last name, middle initial, case sensitivity, and
   * eventually it could answer true to wild cards and
   * regular expressions.
   */
  public boolean nameEquals( String name ) {
    return getName().equalsIgnoreCase( name );
  }
  /** Never returns null. */
  private synchronized String getName() {
    if( this.name == null ) {
      this.name == "";
    }
    return this.name;
  }
}
Questions
- How is the LoD broken?
 - Where is the code breaking the LoD?
 - How should the code be written to uphold the LoD?
 
© Stack Overflow or respective owner