My application loads lots of data from a database into a complex data structure. The in-memory data structure ressembles the structure of the database, which means that if the database contains the following tables:
- table A, key is A1
- table B, key is B1, one of the columns is a foreign key to [the key of] table A
- table C, key is C1, one of the columns is a foreign key to [the key of] table B
Then I have classes A, B and C, and:
- a data member of B (B::m_a) is a pointer to A
- a data member of C (C::m_b) is a pointer to B
This implies that if I load the database, that I have to load it in the correct order. If I first load C, then it will complain that it cannot set the value C::m_b because the instance where it should point to was not loaded.
Problem is when there is also a column in A that is a foreign key to one of the other tables, let's say C.
I could solve the problem by loading all foreign keys as strings, and then perform a lookup after all the data has been loaded, but since I sometimes have to load millions of records, I can't afford to spend memory on these (albeit temporary) strings.
Having read about good design (e.g. the book "Large Scale C++ Software Design") it seems to me that it's a bad idea to have circular references at all. E.g. if file X.H includes Y.H, but Y.H also includes X.H you probably have a bad design; if class X depends on class Y and vice versa you probably have a bad design, which should be solved by extracting this dependency and introducing a third class Z, which depends on X and Y (X and Y won't depend on eachother anymore).
Is it a good idea to also extend this design-rule to database design? In other words: preventing circular references in foreign keys.