【问题标题】:SELECTING with multiple WHERE conditions on same column在同一列上使用多个 WHERE 条件进行选择
【发布时间】:2011-05-02 03:22:56
【问题描述】:

好的,我想我可能在这里忽略了一些明显/简单的事情......但我需要编写一个查询,只返回与同一列上的多个条件匹配的记录......

我的表格是一个非常简单的链接设置,用于将标志应用到用户...

ID   contactid  flag        flag_type 
-----------------------------------
118  99         Volunteer   1 
119  99         Uploaded    2 
120  100        Via Import  3 
121  100        Volunteer   1  
122  100        Uploaded    2

等等...在这种情况下,您会看到联系人 99 和 100 都被标记为“志愿者”和“已上传”...

我需要做的是返回那些仅与通过搜索表单输入的多个条件匹配的联系人 ID...联系人 ID 必须匹配所有选择的标志...在我的脑海中,SQL 应该类似于:

SELECT contactid 
 WHERE flag = 'Volunteer' 
   AND flag = 'Uploaded'...

但是...什么都没有返回...我在这里做错了什么?

【问题讨论】:

  • 此语句无效,因为 flag 不能同时等于 'Volunteer' 和 'Upload'。您可以使用 OR 运算符代替 AND,它会起作用。

标签: mysql sql aggregate-functions where-clause


【解决方案1】:

这样的东西应该适合你

SELECT * FROM `product_options` GROUP BY product_id 
HAVING COUNT(option_id IN (1,2,3) OR NULL) > 0 AND COUNT(option_id IN (7) OR NULL) > 0

【讨论】:

    【解决方案2】:

    使用这个: 例如:

    select * from ACCOUNTS_DETAILS
    where ACCOUNT_ID=1001
    union
    select * from ACCOUNTS_DETAILS
    where ACCOUNT_ID=1002
    

    【讨论】:

      【解决方案3】:
      SELECT contactid, Count(*) 
      FROM <YOUR_TABLE> WHERE flag in ('Volunteer','Uploaded')  
      GROUP BY contactid 
      HAVING count(*)>1;
      
      【解决方案4】:

      考虑像这样使用 INTERSECT:

      SELECT contactid WHERE flag = 'Volunteer' 
      INTERSECT
      SELECT contactid WHERE flag = 'Uploaded'
      

      我认为这是最符合逻辑的解决方案。

      【讨论】:

      • 由于提问者标记了mysql,我认为最好指出INTERSECT不适用于MySql
      • 提问者可能已经标记了 mysql,但对这个工作得很好的 TSQL 用户竖起大拇指。
      【解决方案5】:

      将 AND 更改为 OR。简单的错误。把它想象成简单的英语,我想选择任何等于这个或那个的东西。

      【讨论】:

        【解决方案6】:
        select purpose.pname,company.cname
        from purpose
        Inner Join company
        on purpose.id=company.id
        where pname='Fever' and cname='ABC' in (
          select mname
          from medication
          where mname like 'A%'
          order by mname
        ); 
        

        【讨论】:

          【解决方案7】:

          尝试使用这个备用查询:

          SELECT A.CONTACTID 
          FROM (SELECT CONTACTID FROM TESTTBL WHERE FLAG = 'VOLUNTEER')A , 
          (SELECT CONTACTID FROM TESTTBL WHERE FLAG = 'UPLOADED') B WHERE A.CONTACTID = B.CONTACTID;
          

          【讨论】:

            【解决方案8】:

            AND 仅当您的列中同时存在volunteeruploaded 时才会返回答案。否则它将返回null 值...

            尝试在您的声明中使用OR ...

            SELECT contactid  WHERE flag = 'Volunteer' OR flag = 'Uploaded'
            

            【讨论】:

            • 这将显示所有 VolunteerUploaded 的条目,但他希望条目有两次,每个条目一次
            【解决方案9】:

            有时你只见树木不见森林 :)

            你原来的 SQL ..

            SELECT contactid 
             WHERE flag = 'Volunteer' 
               AND flag = 'Uploaded'...
            

            应该是:

            SELECT contactid 
             WHERE flag = 'Volunteer' 
               OR flag = 'Uploaded'...
            

            【讨论】:

            • 我不相信这会返回 OP 所需的结果。 contactIds 需要匹配所有标志,而不是其中的一个或多个。
            【解决方案10】:

            您可以使用GROUP BYHAVING COUNT(*) = _

            SELECT contact_id
            FROM your_table
            WHERE flag IN ('Volunteer', 'Uploaded', ...)
            GROUP BY contact_id
            HAVING COUNT(*) = 2 -- // must match number in the WHERE flag IN (...) list
            

            (假设contact_id, flag 是唯一的)。

            或者使用连接:

            SELECT T1.contact_id
            FROM your_table T1
            JOIN your_table T2 ON T1.contact_id = T2.contact_id AND T2.flag = 'Uploaded'
            -- // more joins if necessary
            WHERE T1.flag = 'Volunteer'
            

            如果标志列表很长并且有很多匹配项,则第一个可能更快。如果标志列表很短并且匹配项很少,您可能会发现第二个更快。如果性能是一个问题,请尝试对您的数据进行测试,看看哪个效果最好。

            【讨论】:

            • JOIN 的问题是,如果有多个与“已上传”标志相关联的联系人 ID 记录,则 T1 引用将重复。
            • SELECT contact_id FROM your_table WHERE ( flag IN ('Volunteer', 'Uploaded', ...) and one_type = sometype_one ) AND flag IN ('someOtherVolunteer', 'Uploaded', ...)和 second_type = sometype_two GROUP BY contact_id HAVING COUNT(*) = 2 先生,我有与上述查询相同的 senario,但它返回 null。零行。
            • 在自联接的情况下,对于 N 个值,您需要 N 个自联接。在该示例中,如果您必须获得包含所有这三个标志“已上传”、“志愿者”和“通过导入”的结果怎么办?所以,我认为使用GROUP BYHAVING COUNT 更有意义。
            【解决方案11】:

            用途:

              SELECT t.contactid
                FROM YOUR_TABLE t
               WHERE flag IN ('Volunteer', 'Uploaded')
            GROUP BY t.contactid
              HAVING COUNT(DISTINCT t.flag) = 2
            

            关键是t.flag 的计数需要等于IN 子句中的参数数量。

            COUNT(DISTINCT t.flag) 的使用是为了防止对 contactid 和标志的组合没有唯一约束——如果没有重复的机会,您可以从查询中省略 DISTINCT:

              SELECT t.contactid
                FROM YOUR_TABLE t
               WHERE flag IN ('Volunteer', 'Uploaded')
            GROUP BY t.contactid
              HAVING COUNT(t.flag) = 2
            

            【讨论】:

              【解决方案12】:

              无法真正看到您的桌子,但标志不能同时是“志愿者”和“已上传”。如果一列中有多个值,则可以使用

              WHERE flag LIKE "%Volunteer%" AND flag LIKE "%UPLOADED%"
              

              查看格式化表格并不适用。

              【讨论】:

                猜你喜欢
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                • 2021-11-17
                • 1970-01-01
                • 2011-03-31
                • 2020-08-11
                相关资源
                最近更新 更多