2012-09-07 37 views
2

我有3个表如下SQL查询,以避免环或游标读取记录

Table #1 has column UserId and UserName 

Table #2 has column MenuId and MenuName 

Table #3 has column MappingId, UserId, MenuId 

(在表#3列的用户ID和MENUID分别具有表#1用户id和表#2 MENUID外键关系。)

我想选择语句,如果用户名和MENUNAME组合表#3已经存在,否则它会像假

UserName, MenuName, AllowedDisallowedFlag 

Where 

UserName is Names of User From Table #1 

MenuName is Names of Menu from Table #2 

AllowedDisallowedFlag将是真实的。

有什么办法可以在不使用游标或循环的情况下实现这一点吗?

+3

是的,正常的SQL方法是使用[joins](http://en.wikipedia.org/wiki/Join_(SQL))。 – Oded

+0

@oded你可以帮我查询吗?我的意思是如何使用连接实现这个? –

回答

3

你需要的东西是这样的:

SELECT DISTINCT 
    UserName, 
    MenuName, 
    CASE WHEN Table3.UserID IS NULL THEN 0 ELSE 1 END AS Allowed 
    FROM Table1 
    CROSS JOIN Table2 
    LEFT JOIN Table3 ON Table1.UserID = Table3.userID 
    AND Table3.MenuID = Table2.MenuID 

这里是一个SQL Fiddle

+0

+1虽然你也没有考虑到用户和menu_的组合实际上是什么意思。 –

+0

是它的工作原理唯一的变化是在case语句 SELECT DISTINCT 用户名, MENUNAME, **允许= ** CASE WHEN Table3.UserID为null,则0 ELSE 1 **完** FROM表1 CROSS JOIN表2 LEFT JOIN表3 ON Table1.UserID = Table3.userID AND Table3.MenuID = Table2.MenuID –

+0

@TimSchmelter我想,如果有表3中没有记录,如用户A + B菜单这意味着B菜单不允许用户A,所以标志应该是0.你认为OP有其他逻辑吗?这似乎是一个简单的menurigth存储问题。 –

0

请尝试查询(我还没有执行):

SELECT 
(SELECT UserName FROM Table#1 T1 WHERE T1.UserId=T2.UserID) AS UserName, 
(SELECT MenuName FROM Table#2 T3 WHERE T3.MenuId=T2.MenuID) AS MenuName, 
(CASE WHEN ISNULL(UserId,'')<>'' AND ISNULL(MenuID,'')<>'' THEN TRUE ELSE FALSE END) AS AllowedDisallowedFlag FROM Table#3 T2 

注:提供的用户名和菜单ID是独特的。

+1

不让我把这样的问题像这样我想在第一列中的第二列菜单名称中的所有用户名(全部存在于表#1中)(表2中针对每个用户名存在的所有菜单)以及第三列如果用户名映射到表#3中的菜单ID,则返回true否则为false –

+0

请尝试此操作:select t1.UserName,t2.MenuName, (CASE WHEN(SELECT COUNT(*)FROM Table_3 t3 where t3.UserID = t1。 UserID和t3.MenuID = t2.MenuID)> 0 then 1 else 0 end)AS AllowedDisallowedFlag 从Table_1 t1,Table_2 t2' – TechDo

+0

是这个给我所需的输出 –