Avoiding loading the same entity multiple times

For this discussion assume I’ve got students and teachers as entities. Each student has exactly one teacher as mapped by foreign key. To make it easy I know that the students are 1 and 2 in the database.

$student1 = Student::model()->findByPk(1);

$student2 = Student::model()->findByPk(2);

$teacher1 = $student1->teacher; //id 1

$teacher2 = $student2->teacher; //id 1

Now if both students have the SAME teacher (teacher ID 1) you’d expect there to be only 1 database call and only one object in memory. Yii loads the teacher entity from the database twice. It creates two separate and completely unrelated objects. (As determinede by spl_object_hash or by changing properties on one object and not having them change on the second object.)

Is there any way to avoid this behavior? My situation involves a LOT more objects than this example and my production server is crashing because of memory overload.

A short but instructive discussion can be found here.

IMHO, Active Record (with or without Identity Map) works best for CRUD-like operations. For batch-processing a large amount of data, I’d choose plain SQL.

I think I’ll just do it myself by overriding the CActiveRecord::instantiate function. I’m doing processing for display of large numbers of objects, not saving to the db. All the business logic is in the objects so I can’t do it in sql.

Do you need to load all the objects into memory at once? Could you not employ some kind of pagination so you only work with a subset of the data at a time? One thing I’ve done in the past is to have a loop in a loop where the outer loop fetches a page of data and the inner loop goes through that page, keeping the number of objects in memory small at any point in time but still working through the full data set.