另一个案例是给出一个设计糟糕,相当古老的数据库并被告知要从中提取有用的信息。我确实讲了很多SQL,但这超出了我的知识。坦率地说,我碰壁了。
所以我给了一个包含几个表的SQLite DB。有趣的是表格节点和关联。
表节点包含所有元素,例如用户,设备(PC),但更多诸如桌面电话设备,办公室电话号码,操作系统,基本上所有内容和任何内容。这是一个样本:
id title entity_type
-----------------------------------
1 user1 User
2 user2 User
3 pc1 Device
4 user3 User
5 pc2 Device
6 pc3 Device
7 pc4 Device
8 os1 OS
9 phon1 Phone
10 os2 OS
11 phon2 Phone
11 phon3 Phone
表关联将设备映射到用户,但还包含更多垃圾映射,例如PC操作系统,办公室电话等。
id parent child
-----------------------------
1 3 1
2 5 2
3 6 4
4 7 4
5 3 8
6 5 8
7 6 10
所以关联将pc1与user1,pc2与user2,pc3和pc4与user3映射,还将os1映射到pc1和pc2,os2到pc3等。 值得庆幸的是,用户只有PC ,没有其他项目映射到用户。
我被要求编制一个列表,显示所有PC以及分配给他们的用户。基本上我需要得到:
user1 pc1
user2 pc2
user3 pc3
user3 pc4
我的想法是:
SELECT nodes.id,title,parent
FROM nodes
INNER JOIN associations ON nodes.id = associations.child
WHERE entity_type = "User"
ORDER BY id;
到目前为止,这为我提供了所有用户以及属于他们的父母(例如,节点中的PC ID)的列表。我不知道如何替换父,我现在只是一个数字,引用节点中的ID,并带有此项的标题。
任何帮助?
答案 0 :(得分:0)
您需要对同一个表使用多个连接 - 例如:
select user.title as user, pc.title as pc
from nodes as user
join associations as a on a.child=user.id
join nodes as pc on a.parent=pc.id
where user.entity_type = 'User'
关于评论中提到的“笔记本的父母+ 1”逻辑:如果我理解正确,当PC的标题是“移动”时,它是一个笔记本,下一个id的节点是真实标题。
select user.title as user, ifnull(nb.title, pc.title) as computer
from nodes as user
join associations as a on a.child=user.id
join nodes as pc on a.parent=pc.id
left join nodes as nb on pc.title='mobile' and nb.id = pc.id + 1
where user.entity_type = 'User'
使用left join
表示如果电脑标题不'移动',则nb
字段全部为null
,并在填充时填充ifnull
是。 select
中的Rng.Value2 = Replace(Rng.Value2, Left(Rng.Value2, I - 1), "")
应确保每行都使用正确的标题。
答案 1 :(得分:0)
这是一个将提取所有用户与节点关系的查询。它并不假设用户只是子节点:
$groups = [];
foreach($arr as $val) {
$groups[] = ['first_key_name' => $val->ID, 'second_key_name' => $val->login];
}