这个SQL极难,绝对需要高手!!!

APOLLO_TS 2009-05-11 06:24:45
CREATE TABLE IF NOT EXISTS T_ACC_ROLE (
ACC_ROLE_ID INT(11) NOT NULL AUTO_INCREMENT COMMENT '编号ID',
ROLE_ID int(4) NOT NULL COMMENT '角色ID',
PRIORITY int(4) default NULL COMMENT '优先权',
INFO int(4) default NULL COMMENT '信息',
PRIMARY KEY(ACC_ROLE_ID)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

CREATE TABLE IF NOT EXISTS T_ACC_ROLE_NOR (
ACC_ROLE_ID INT(11) NOT NULL AUTO_INCREMENT COMMENT '编号ID',
ROLE_ID int(4) NOT NULL COMMENT '角色ID',
INFO int(4) default NULL COMMENT '信息',
PRIMARY KEY(ACC_ROLE_ID)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

T_ACC_ROLE 数据
ACC_ROLE_ID ROLE_ID PRIORITY INFO
1 2 1 11
2 2 2 12
3 2 3 13
4 4 1 14

T_ACC_ROLE_NOR 数据
ACC_ROLE_ID ROLE_ID INFO
1 2 16
2 3 17
4 5 19

要采集这两个表的INFO,INFO在两个表中不会重复。但是T_ACC_ROLE 中有重复的ROLE_ID,这时候要PRIORITY 较小的信息,说白了是优先级别较高的信息。但是在T_ACC_ROLE_NOR 也有ROLE_ID,那么表T_ACC_ROLE_NOR 中的信息处于更高的优先级,那么就采用T_ACC_ROLE_NOR的信息。

算法过程:

例如:搜索表T_ACC_ROLE
有三个ROLE_ID=2的信息,取PRIORITY =1的信息。
但是在T_ACC_ROLE_NOR表中也有ROLE_ID=2的信息,那么T_ACC_ROLE 表的信息就是旧信息,不采用,使用T_ACC_ROLE_NOR 的信息。

最后结果是:

ROLE_ID INFO
2 16
3 17
4 14
5 19
...全文
211 9 打赏 收藏 转发到动态 举报
写回复
用AI写文章
9 条回复
切换为时间正序
请发表友善的回复…
发表回复
allenkangning888 2009-05-19
  • 打赏
  • 举报
回复
呵呵,不错,高手...
yuanwen1314 2009-05-19
  • 打赏
  • 举报
回复
置顶高手来也
magnet2008 2009-05-12
  • 打赏
  • 举报
回复
create procedure info()
begin
declare var1 integer;
declare var2 integer;
declare found boolean default true;
declare cur cursor for
select t2,min(t3) from b1
where t2 not in
(select t6 from b2)
group by t2 order by t2;
declare continue handler for not found
set found=false;
create temporary table tt1
( id integer,
info integer);
insert into tt1
( select t6,t7
from b2);
open cur;
fetch cur into var1,var2;
while found do
insert into tt1
(select t2,t4 from b1
where t2=var1
and t3=var2);
fetch cur into var1,var2;
end while;
close cur;
select * from tt1
group by 1;
end
结果
+------+------+
| id | info |
+------+------+
| 2 | 16 |
| 3 | 17 |
| 4 | 14 |
| 5 | 19 |
+------+------+
我写的一个存储过程,希望有用。
APOLLO_TS 2009-05-12
  • 打赏
  • 举报
回复
[Quote=引用 2 楼 ACMAIN_CHM 的回复:]
楼上正解。
另外一种变形的写法如下,其实和上面小梁的一样。只不过用left join 替代了exists

SQL code
select a.ROLE_ID,a.INFO
from (T_ACC_ROLE a left join T_ACC_ROLE b on a.ROLE_ID=b.ROLE_ID and a.PRIORITY<b.PRIORITY)
left join T_ACC_ROLE_NOR on a.ROLE_ID=T_ACC_ROLE_NOR.ROLE_ID
where b.ROLE_ID is null and T_ACC_ROLE_NOR.ROLE_ID is null
union all
select ROLE_ID,INFO
from T_ACC_ROLE_NOR

[/Quote]

谢谢!!但是有点小错。a.PRIORITY>b.PRIORITY 阁下的意思是优先将T_ACC_ROLE 中存在而T_ACC_ROLE_NOR不存在的数据取出来。
所以>将会把最小的PRIORITY左联不成功。

真的很棒。。我在测几下!!




wwwwb 2009-05-12
  • 打赏
  • 举报
回复
实际上就是两表没有对应ROLE_ID 的记录+
如果有对应ROLE_ID 的记录,则取T_ACC_ROLE_NOR表的 数据

select a.ROLE_ID,a.info from T_ACC_ROLE a left join
t_acc_role_nor b on a.ROLE_ID=b.ROLE_ID where b.ROLE_ID is null
union all
select b.ROLE_ID,b.info from T_ACC_ROLE a right join
t_acc_role_nor b on a.ROLE_ID=b.ROLE_ID where a.ROLE_ID is null
union all
select distinct a.ROLE_ID,a.INFO from t_acc_role_nor a inner join t_acc_role b
on a.ROLE_ID=b.ROLE_ID
order by role_id
yuanwen1314 2009-05-12
  • 打赏
  • 举报
回复
上面都是高手
ACMAIN_CHM 2009-05-11
  • 打赏
  • 举报
回复

楼上正解。
另外一种变形的写法如下,其实和上面小梁的一样。只不过用left join 替代了exists

select a.ROLE_ID,a.INFO
from (T_ACC_ROLE a left join T_ACC_ROLE b on a.ROLE_ID=b.ROLE_ID and a.PRIORITY<b.PRIORITY)
left join T_ACC_ROLE_NOR on a.ROLE_ID=T_ACC_ROLE_NOR.ROLE_ID
where b.ROLE_ID is null and T_ACC_ROLE_NOR.ROLE_ID is null
union all
select ROLE_ID,INFO
from T_ACC_ROLE_NOR


liangCK 2009-05-11
  • 打赏
  • 举报
回复
mysql> -- -------------------------------
mysql> -- Author: liangCK 小梁
mysql> -- -------------------------------
mysql>
mysql> -- > 生成测试数据: [T_ACC_ROLE]
mysql> DROP TABLE IF EXISTS T_ACC_ROLE;
Query OK, 0 rows affected (0.00 sec)

mysql> CREATE TABLE T_ACC_ROLE (ACC_ROLE_ID INT,ROLE_ID INT,PRIORITY INT,INFO INT);
Query OK, 0 rows affected (0.03 sec)

mysql> INSERT INTO T_ACC_ROLE
-> SELECT 1,2,1,11 UNION ALL
-> SELECT 2,2,2,12 UNION ALL
-> SELECT 3,2,3,13 UNION ALL
-> SELECT 4,4,1,14;
Query OK, 4 rows affected (0.00 sec)
Records: 4 Duplicates: 0 Warnings: 0

mysql>
mysql> -- > 生成测试数据: [T_ACC_ROLE_NOR]
mysql> DROP TABLE IF EXISTS T_ACC_ROLE_NOR;
Query OK, 0 rows affected (0.00 sec)

mysql> CREATE TABLE T_ACC_ROLE_NOR (ACC_ROLE_ID INT,ROLE_ID INT,INFO INT);
Query OK, 0 rows affected (0.05 sec)

mysql> INSERT INTO T_ACC_ROLE_NOR
-> SELECT 1,2,16 UNION ALL
-> SELECT 2,3,17 UNION ALL
-> SELECT 4,5,19;
Query OK, 3 rows affected (0.00 sec)
Records: 3 Duplicates: 0 Warnings: 0

mysql>
mysql> -- SQL查询如下:
mysql>
mysql> SELECT ROLE_ID,INFO FROM T_ACC_ROLE_NOR
-> UNION ALL
-> SELECT ROLE_ID,INFO FROM T_ACC_ROLE AS A
-> WHERE NOT EXISTS(SELECT * FROM T_ACC_ROLE_NOR WHERE ROLE_ID=A.ROLE_ID)
-> AND NOT EXISTS(SELECT * FROM T_ACC_ROLE WHERE A.ROLE_ID=ROLE_ID AND PRIORITY<A.PRIORITY)
-> ORDER BY 1;
+---------+------+
| ROLE_ID | INFO |
+---------+------+
| 2 | 16 |
| 3 | 17 |
| 4 | 14 |
| 5 | 19 |
+---------+------+
4 rows in set (0.00 sec)

56,677

社区成员

发帖
与我相关
我的任务
社区描述
MySQL相关内容讨论专区
社区管理员
  • MySQL
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧