Setting up a "to-many" relationship value dependency for a transient Core Data attribute
- by Greg Combs
I've got a relatively complicated Core Data relationship structure and I'm trying to figure out how to set up value dependencies (or observations) across various to-many relationships. Let me start out with some basic info. I've got a classroom with students, assignments, and grades (students X assignments). For simplicity's sake, we don't really have to focus much on the assignments yet.
StudentObj <--->> ScoreObj <<---> AssignmentObj
Each ScoreObj has a to-one relation with the StudentObj and the AssignmentObj.
ScoreObj has real attributes for the numerical grade, the turnInDate, and notes.
AssignmentObj.scores is the set of Score objects for that assignment (N = all students).
AssignmentObj has real attributes for name, dueDate, curveFunction, gradeWeight, and maxPoints.
StudentObj.scores is the set of Score objects for that student (N = all assignments).
StudentObj also has real attributes like name, studentID, email, etc.
StudentObj has a transient (calculated, not stored) attribute called gradeTotal.
This last item, gradeTotal, is the real pickle. it calculates the student's overall semester grade using the scores (ScoreObj) from all their assignments, their associated assignment gradeWeights, curves, and maxPoints, and various other things.
This gradeTotal value is displayed in a table column, along with all the students and their individual assignment grades. Determining the value of gradeTotal is a relatively expensive operation, particularly with a large class, therefore I want to run it only when necessary. For simplicity's sake, I'm not storing that gradeTotal value in the core data model. I don't mind caching it somewhere, but I'm having a bitch of a time determining where and how to best update that cache.
I need to run that calculation for each student whenever any value changes that affects their gradeTotal. If this were a simple to-one relationship, I know I could use something like keyPathsForValuesAffectingGradeTotal ... but it's more like a many-to-one-to-many relationship. Does anyone know of an elegant (and KVC correct) solution? I guess I could tear through all those score and assignment objects and tell them to register their students as observers. But this seems like a blunt force approach.