比较SQL中的值,如果匹配则返回true,否则为false

时间:2015-08-10 07:02:38

标签: sql-server sql-server-2008

我有一个应用程序,允许用户互相联系,将其视为约会网站。我在联系人部分周围添加了一些安全措施,用户可以通过设置特定的年龄/身高范围和性别来限制谁可以联系他/她。

例如,我点击UserId-2配置文件,然后这将调用数据库,传入ID或选择的配置文件并传入我的ID,然后调用我的函数传递这两个值。功能如下:

ALTER FUNCTION [dbo].[Can_User_Contact] 
(
  @UserId1 int = 2, -- UserId
  @UserId2 int = 1 -- Requested by Id
)
  RETURNS bit
  AS
  BEGIN
  RETURN (

  SELECT CASE WHEN up.Id IS NULL THEN 0 ELSE 1 END AS does_data_match
  FROM [user].User_Settings us
  LEFT OUTER JOIN [User].[User_Profile] up ON us.UserId = @UserId1 
  LEFT OUTER JOIN [User].[User_Details] d ON up.Id = d.UserId
  AND up.id = @UserId2 
  AND d.Height between ISNULL(us.HeightFrom, d.height) and ISNULL(us.HeightTo, d.Height) 
  AND up.Age between ISNULL(us.AgeFrom, up.age) and ISNULL(us.AgeTo, up.Age)
  AND up.Gender = ISNULL(us.Gender, up.Gender)

)  
END 

在这个函数中,我将UserId-2在设置表中保存的值与我自己的值进行比较,方法是加入用户配置文件表和用户详细信息表,这个问题就是每次执行它我得到的以下消息:

Subquery returned more than 1 value. This is not permitted when the subquery follows =, !=, <, <= , >, >= or when the subquery is used as an expression.

我在设置表中有两条记录,如下所示:

enter image description here

我只对第二张唱片感兴趣。

有人可以对我可能做错的事情有所了解吗?

@ UserId1是个人资料ID, @ UserId2是请求查看它的用户。

请记住,@ UserId1的设置表中可能没有记录,此功能也是可选的。

2 个答案:

答案 0 :(得分:1)

SELECT查询返回多行。 由于您对单个值的使用感兴趣,所以:

ALTER FUNCTION [dbo].[Can_User_Contact] 
        (
          @UserId1 int = 2, -- UserId
          @UserId2 int = 1 -- Requested by Id
        )
        RETURNS bit
        AS
        BEGIN
          RETURN 
          (
            SELECT CASE WHEN EXISTS  
            (  
                SELECT 1 FROM [user].User_Settings us1
                  LEFT OUTER JOIN [User].[User_Profile] up ON up.id = @UserId2
                  LEFT OUTER JOIN [User].[User_Details] d ON up.Id = d.UserId 
                  LEFT OUTER JOIN [user].[User_Settings] us2 ON us2.UserId=up.id
              WHERE  
                  d.Height between ISNULL(us1.HeightFrom, d.height) and ISNULL(us1.HeightTo, d.Height) 
                  AND us2.Age between ISNULL(us1.AgeFrom, up.age) and ISNULL(us1.AgeTo, up.Age)
                  AND us1.Gender = ISNULL(us2.Gender, up.Gender)
                  AND up.Id IS NOT NULL 
                  AND  us1.UserId = @UserId1
            )   THEN 1 ELSE 0 END AS does_data_match  
        END 

答案 1 :(得分:1)

假设您为每个用户设置了user_settingUser_ProfileUser_Details的条目,这应该可以。

根据您的结果,您的加入条件会出现问题。理想情况下,您的某些加入条件应该是WHERE条款的一部分,例如up.id = @UserId2

<强>查询

  SELECT TOP 1 CASE WHEN us.UserId IS NULL THEN 0 ELSE 1 END AS does_data_match
  FROM [User].[User_Profile] up
  INNER JOIN [User].[User_Details] d ON up.Id = d.UserId
  LEFT OUTER JOIN  [user].User_Settings us
  ON us.UserId = @UserId1 
  AND d.Height between ISNULL(us.HeightFrom, d.height) and ISNULL(us.HeightTo, d.Height) 
  AND up.Age between ISNULL(us.AgeFrom, up.age) and ISNULL(us.AgeTo, up.Age)
  AND up.Gender = ISNULL(us.Gender, up.Gender)
 WHERE up.id = @UserId2
ORDER BY up.id ASC

注意:如果假设为真,那么理想情况下不需要TOP。只是添加了它以增加安全性