Background:
I am working on a large database that is used to track wire footages. Currently, the database (Oracle) is structured around three main tables:
1) A map detail table. Defines all of the top-level details of a particular map such as county / district / city. Each map is uniquely identified by a serial number that is used in the following tables.
2) A corridor length table. Basically, how long a run of wire is as the crow flies and if that corridor is on public or private land. Thus, the footage defined here is simply the distance from A to B.
3) A wire length table. This table stores information about the different wires that can be run in a given corridor. There is one row for each operating voltage. Thus, a corridor may have several lengths of wire at, for example; 12KV, 33KV, and 66KV.
There will always be a single map record in (1) but there bay be any number of rows in (2) and (3) and the row counts in (2) and (3) usually do not match.
The Question:
I am searching for a method to join these three tables such that each footage is only reported once. This is best illustrated by example. Below is a sample record set:
Map Details:
-------------------------------------------
| SERIAL_NO | CNTY | DIST | MAP_NO (Name) |
|-----------------------------------------|
| 1 | 33 | 88 | 123-4567-8 |
-------------------------------------------
Corridor Details:
------------------------------------
| SERIAL_NO | PROPRTY_CD | CORR_FT |
|----------------------------------|
| 1 | PUBLIC | 100 |
| 1 | PRIVATE | 200 |
------------------------------------
Wire Details
---------------------------------
| SERIAL_NO | OPER_KV | WIRE_FT |
|-------------------------------|
| 1 | 12 | 300 |
| 1 | 33 | 200 |
| 1 | 66 | 200 |
---------------------------------
The ultimate output that I am after would be something like the following:
--------------------------------------------------------------------------------------
| SERIAL_NO | CNTY | DIST | MAP_NO (Name) | PROPRTY_CD | CORR_FT | OPER_KV | WIRE_FT |
|------------------------------------------------------------------------------------|
| 1 | 33 | 88 | 123-4567-8 | PUBLIC | 100 | 12 | 300 |
| 1 | 33 | 88 | 123-4567-8 | PRIVATE | 200 | 33 | 200 |
| 1 | 33 | 88 | 123-4567-8 | NULL | NULL | 66 | 200 |
--------------------------------------------------------------------------------------
NOTE: The wire and corridor footages will not match most of the time (there are wire multipliers and such that are not shown here for brevity’s sake). Also, there may be more rows in the corridor table versus the wire table (a corridor with no wire in it) or vice-versa (a corridor with multiple wires run in it).
I have tried many different approaches to this problem but I can’t seem to get the output I want. Every join I have tried has resulted in values being duplicated as or similar to that which follows:
BAD:
--------------------------------------------------------------------------------------
| SERIAL_NO | CNTY | DIST | MAP_NO (Name) | PROPRTY_CD | CORR_FT | OPER_KV | WIRE_FT |
|------------------------------------------------------------------------------------|
| 1 | 33 | 88 | 123-4567-8 | PUBLIC | 100 | 12 | 300 |
| 1 | 33 | 88 | 123-4567-8 | PUBLIC | 100 | 33 | 200 |
| 1 | 33 | 88 | 123-4567-8 | PUBLIC | 100 | 66 | 200 |
| 1 | 33 | 88 | 123-4567-8 | PRIVATE | 200 | 12 | 300 |
| 1 | 33 | 88 | 123-4567-8 | PRIVATE | 200 | 33 | 200 |
| 1 | 33 | 88 | 123-4567-8 | PRIVATE | 200 | 66 | 200 |
--------------------------------------------------------------------------------------
Summary:
My apologies for the long question, but it is somewhat complex explaining what I am after. Long story short, I want to list all rows in both child tables side by side (in no particular order) while filling in NULL for the columns of the row difference between the two tables. Thank you in advance.
The task in the way you set it up can be brute-forced in the following way
However, if I were you I would concern about questions asked in comments to your initial post 😉