I think you should limit yourself to one table, at least for the purpose of parent<->child relationships. I am working on a similar problem right now. (I started with sqlite, but moved to mysql for reasons outside of this problem scope.) My solution, which performs fine, is as follows:
I put all objects into a single table. The parent_id attribute is used to associate the parent of an entry. Now a query like that SELECT a.id AS content_id, a.parent_id AS ancestor_id FROM contents a WHERE a.parent_id IS NOT NULL UNION SELECT a.id AS content_id, b.parent_id AS ancestor_id FROM contents a INNER JOIN contents b ON a.parent_id=b.id WHERE b.parent_id IS NOT NULL UNION SELECT a.id AS content_id, c.parent_id AS ancestor_id FROM contents a INNER JOIN contents b ON a.parent_id=b.id INNER JOIN contents c ON b.parent_id=c.id WHERE c.parent_id IS NOT NULL selects content_is, ancestor_id pairs up to 4 levels deep. This performs fine with a dataset of 50000 elements, and an average depth of 3..4 I tried this once with 5 levels and it still felt ok. Even faster than that was a query like this SELECT a.id AS aid, a.parent_id AS bid, b.parent_id AS cid, d.parent_id AS did FROM contents a LEFT JOIN contents b ON a.parent_id=b.id LEFT JOIN contents c ON b.parent_id=c.id which obviously might contain NULL entries (e.g. 1, 2, NULL, NULL) in case there are no 4 levels. Another approach would be to maintain a relation table holding all those entries which is updated using triggers. May be this is a direction you could go, too? /eno > I have 5 tables that store records for 5 different types of documents. > Each type of document can be a descendent of a document in one of the > other tables. > > For example, let's call the tables A, B, C, D and E. > > If you create a record in A, and then create a record in B, you can > associate the document in B with the record in A. You could then do > the same with a record in C, D, and E. > > One wrinkle is that you can skip documents, so it's not always a > direct chain. For example, you could have A > B > E. > > Another wrinkle is that you don't have to start at A, so you could > have B > C > D > E. You can actually start at any point in the cycle. > > Another wrinkle is that you can loop back around to other tables > again, so something like A > B > E > A (not the same record as the > first A) > C > E is possible. Of course, you can't link back to a > record that is already in the chain though, so as to avoid and > infinite loop. > > A final wrinkle is that each parent record can have more than one > linked child in other tables. > > Each table has 2 columns: ParentTable and ParentRecordID that hold the > associated record from the immediate parent table for each child > record (or null for records that are at the top of a chain, or > completely unchained at this point). > > Now Table A is kind of special in that I want to be able to figure out > the deepest descendents of all of the records in Table A in any other > tables (if any) and display data from the deepest linked records > (using group_concat on a fields in those linked records). > > So, for example, if we had record chains such as: > D1 < B1 < A1 > D2 < C1 < A3 > E1 < B3 < A1 > E2 < C2 < A1 > C3 < B2 > > I want to be able to show a cell for each record in Table A like: > > TABLE A > A.ID A.Title DeepestDocuments > ------------------------------------------ > 1 Doc1 E.Doc1, E.Doc2 > 2 Doc2 Null > 3 Doc3 D.Doc2 > > You'll notice that even though A1 has descendents in tables B, C and > D, only descendents in Table E are listed in the DeepestDocuments cell > because that is the deepest table with descendents. > > I've got what I need to work by manually looping through records and > running up the chain to see when I get a null parent record to > determine the top level reference, and then concatenating all of the > deepest records fields as required, but it is quite slow. On 100 rows > it can take 3-6 seconds on a reasonably fast computer, but table A > could conceivably contain a few thousand records, which would make it > far too slow for my needs. > > I'm wondering if anyone has any ideas on how I might accomplish what I > need using SQLite supported SQL. I suspect I need to do something with > UNION statements, but my experience with them is non-existent, and > nothing I've tried yet has worked. > > Thanks in advance for any help in this matter. > Jason > _______________________________________________ > sqlite-users mailing list > sqlite-users@sqlite.org > http://sqlite.org:8080/cgi-bin/mailman/listinfo/sqlite-users _______________________________________________ sqlite-users mailing list sqlite-users@sqlite.org http://sqlite.org:8080/cgi-bin/mailman/listinfo/sqlite-users