Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/sql/82.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Sql Oracle:如何在列中仅获取具有特定条件的行_Sql_Oracle - Fatal编程技术网

Sql Oracle:如何在列中仅获取具有特定条件的行

Sql Oracle:如何在列中仅获取具有特定条件的行,sql,oracle,Sql,Oracle,我有三张桌子,顾客,订单和顾客订单如下: Customers: ID NAME 1 Peter 2 Jack 3 Lisa Orders: ID INIT_DATE END_DATE 1 10-11-2014 10-11-2015 2 23-11-2014 01-01-2015 3 23-11-2014 03-05-2015 4 04-04-2016

我有三张桌子,顾客,订单和顾客订单如下:

Customers:
    ID   NAME
    1    Peter
    2    Jack
    3    Lisa

Orders:
    ID   INIT_DATE    END_DATE
    1    10-11-2014   10-11-2015
    2    23-11-2014   01-01-2015
    3    23-11-2014   03-05-2015
    4    04-04-2016   08-11-2016
    5    13-07-2016   01-11-2016
    6    04-06-2016   30-10-2016
    7    12-11-2014   01-05-2015
    8    26-11-2014   10-10-2015
    9    05-09-2016   11-11-2016

Customers_Orders:
   CUSTOMER_ID   ORDER_ID
   1             1
   1             2
   1             3
   2             4
   2             5
   2             6
   3             7
   3             8
   3             9
我需要找到所有订单都过期的客户。我的意思是,那些sysdate不在init_date和end_date之间的订单。在本例中,预期结果为1-Peter

我尝试的是:

SELECT *
FROM Customers
WHERE
ID NOT IN (
  SELECT DISTINCT Customers_Orders.CUSTOMER_ID
  FROM Customers_Orders, Orders
  WHERE Customers_Orders.ORDER_ID = Orders.ID
  AND Orders.INIT_DATE <= SYSDATE AND Orders.END_DATE > SYSDATE
)
但是我不喜欢非语法的,因为它的性能很低。还有别的办法吗

注:日期格式为dd-mm-yyyy


编辑:我用粗体更正了这个问题。

连接三个表,并使用条件聚合检查客户的所有订单是否都过期

select c.id,c.name
from customer_orders co
join orders o on o.id=co.order_id
join customers c on c.id=co.customer_id
group by c.id,c.name
having count(case when sysdate between co.init_date and co.end_date then 1 end) = 0

连接这三个表,并使用条件聚合检查客户的所有订单是否已过期

select c.id,c.name
from customer_orders co
join orders o on o.id=co.order_id
join customers c on c.id=co.customer_id
group by c.id,c.name
having count(case when sysdate between co.init_date and co.end_date then 1 end) = 0

为什么不直接加入呢

  SELECT DISTINCT C.CUSTOMER_ID
    FROM customers c
       JOIN Customers_Orders co on co.customer_id = c.customer_id
       JOIN Orders od on od.order_id = co.order_id
    WHERE Od.INIT_DATE <= SYSDATE 
      AND Od.END_DATE > SYSDATE
通过对订单进行正确的索引,您可以通过将筛选器放入联接来获得性能增益:

  SELECT DISTINCT C.CUSTOMER_ID
    FROM customers c
       JOIN Customers_Orders co on co.customer_id = c.customer_id
       JOIN (SELECT od.order_id 
               from Orders 
               WHERE Od.INIT_DATE <= SYSDATE 
                 AND Od.END_DATE > SYSDATE )  od on od.order_id = co.order_id

但现在我们讨论的是性能调整策略。。。。在这种情况下,我们需要讨论您的数据配置文件等,以获得最佳解决方案。

为什么不直接加入

  SELECT DISTINCT C.CUSTOMER_ID
    FROM customers c
       JOIN Customers_Orders co on co.customer_id = c.customer_id
       JOIN Orders od on od.order_id = co.order_id
    WHERE Od.INIT_DATE <= SYSDATE 
      AND Od.END_DATE > SYSDATE
通过对订单进行正确的索引,您可以通过将筛选器放入联接来获得性能增益:

  SELECT DISTINCT C.CUSTOMER_ID
    FROM customers c
       JOIN Customers_Orders co on co.customer_id = c.customer_id
       JOIN (SELECT od.order_id 
               from Orders 
               WHERE Od.INIT_DATE <= SYSDATE 
                 AND Od.END_DATE > SYSDATE )  od on od.order_id = co.order_id

但现在我们讨论的是性能调整策略。。。。在这种情况下,我们需要讨论您的数据配置文件等,以获得最佳解决方案。

这将排除初始日期小于今天且结束日期>今天的所有客户

with Curr_ord as
(
select co1.customer_id, co1.order_id
from  customers_orders co1
inner join orders o1
on o1.id = co1.order_id
where o1.INIT_DATE <= sysdate
and o1.END_DATE > sysdate
)

select C1.*
from Customers C1
left join Curr_Ord CO2
on C1.Customer_ID = CO2.Customer_ID

where CO2.Customer_ID is null

这将排除初始日期小于今天且结束日期>今天的所有客户

with Curr_ord as
(
select co1.customer_id, co1.order_id
from  customers_orders co1
inner join orders o1
on o1.id = co1.order_id
where o1.INIT_DATE <= sysdate
and o1.END_DATE > sysdate
)

select C1.*
from Customers C1
left join Curr_Ord CO2
on C1.Customer_ID = CO2.Customer_ID

where CO2.Customer_ID is null

peter的订单是如何过时的?他的所有订单都在2015年结束,sysdate不在起始日期和结束日期之间`您的数据模型允许多个客户下订单,这可能不是您想要的。我会在表格订单上放置一个客户ID。请看我更正了这个问题,谢谢@LamakHow peter的订单是否过时了?,他的所有订单都在2015年结束,sysdate不在起始日期和结束日期之间。您的数据模型允许多个客户下订单,这可能不是您想要的。我会在订单上放置一个客户ID。请看,我更正了这个问题,谢谢@Lamakb,因为这只会返回有订单的客户。我需要所有订单都过期的客户。因为这只返回有订单正在进行的客户。我需要所有订单都过期的客户。