简体   繁体   English

Oracle:在Where子句中使用案例声明

[英]Oracle: Using Case Statement in Where Clause

In Oracle 12 (and APEX) I am having problems with a CASE statement in a WHERE clause. 在Oracle 12(和APEX)中,WHERE子句中的CASE语句出现问题。 The scenario is a master table, ORDER, and a PRODUCTS_BOUGHT table, so this is a one to many relationship. 该方案是一个主表,一个ORDER和一个PRODUCTS_BOUGHT表,因此这是一对多关系。 I have a report, with a filter on PRODUCTS_BOUGHT. 我有一个报告,其中包含关于PRODUCTS_BOUGHT的过滤器。 The filter populates a bind variable/APEX page item called :P36_PRODUCT_LISTING. 过滤器填充一个名为:P36_PRODUCT_LISTING的绑定变量/ APEX页面项目。 If the user selects a given product, I want the report to just show those orders which contain the given product. 如果用户选择了给定产品,我希望报告仅显示包含给定产品的那些订单。 The filter contains the word 'All', which should not do any filtering, as well as each product we carry. 过滤器包含单词“ All”(不进行任何过滤)以及我们携带的每种产品。

My SQL statement is 我的SQL语句是

Select distinct   
    :P36_PRODUCT_LISTING,    
     LISTAGG(product_name, ', ') WITHIN GROUP (ORDER BY product_name)   OVER (PARTITION BY B.SALES_ORDER_NUMBER) AS products,
    ...
from ORDER A, PRODUCTS_BOUGHT B
where 
 A.SALES_ORDER_NUMBER = B.SALES_ORDER_NUMBER
 and
case when
 :P36_PRODUCT_LISTING = 'All' then 1 = 1
else a.SALES_ORDER_NUMBER IN (SELECT SALES_ORDER_NUMBER from PRODUCTS_BOUGHT where PRODUCT_NAME = :P36_PRODUCT_LISTING) end 

When I run the statement, the error I get is Missing Keyword. 当我运行该语句时,我得到的错误是缺少关键字。 What am I doing wrong? 我究竟做错了什么?

Don't use case . 不要用case Just use boolean logic: 只需使用布尔逻辑:

where (:P36_PRODUCT_LISTING = 'All' or
       a.SALES_ORDER_NUMBER IN (SELECT SALES_ORDER_NUMBER
                                from PRODUCTS_BOUGHT
                                where PRODUCT_NAME = :P36_PRODUCT_LISTING
                               ) 
      ) 

The problem with the case (as you have written it) is that Oracle does not treat the value from a logical expression as a valid value. 这种case的问题(如您所写)是Oracle不会将逻辑表达式中的值视为有效值。 Some databases do, but not Oracle. 某些数据库可以,但是Oracle不可以。

In addition: 此外:

  • Don't use commas in the from clause. 不要在from子句中使用逗号。 Always use proper, explicit join syntax. 始终使用正确的显式join语法。
  • Use table aliases that are abbreviations for the table names. 使用表别名(表名称的缩写)。 Much easier to read the queries and fix bugs. 阅读查询和修复错误要容易得多。
  • select distinct should not be necessary here. 在这里不必select distinct You are doing an aggregation without a group by , so there is only one row anyway. 您正在进行汇总,但没有group by ,因此总之只有一行。

So: 所以:

 Select :P36_PRODUCT_LISTING,    
        LISTAGG(b.product_name, ', ') WITHIN GROUP (ORDER BY b.product_name)   OVER (PARTITION BY B.SALES_ORDER_NUMBER) AS products,
    ...
from ORDER o join
     PRODUCTS_BOUGHT B
     on p.SALES_ORDER_NUMBER = B.SALES_ORDER_NUMBER
    where (:P36_PRODUCT_LISTING = 'All' or
           o.SALES_ORDER_NUMBER IN (SELECT SALES_ORDER_NUMBER
                                    from PRODUCTS_BOUGHT
                                    where PRODUCT_NAME = :P36_PRODUCT_LISTING
                                   ) 
          ); 

Case is designed to return a value, not a statement.. Case旨在返回一个值,而不是一个语句。

Try OR instead 尝试使用OR

where :P36_PRODUCT_LISTING = 'All' 
or (:P36_PRODUCT_LISTING <> 'All'
    and a.SALES_ORDER_NUMBER IN (SELECT SALES_ORDER_NUMBER from PRODUCTS_BOUGHT where PRODUCT_NAME = :P36_PRODUCT_LISTING))

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM