2016-08-22 46 views
1

要衡量免费产品获取新客户的有效性,我希望找到在收到免费订单后支付订单的客户数量。我的表如下所示:在其他条件行之后查找某些条件的行

id | user | total 
----------------- 
1 1  0.00 
2 1  57.33 
3 2  58.21 
4 2  0.00 
5 3  26.10 
6 3  0.00 
7 3  64.94 
8 4  0.00 
9 5  34.54 

在这个表中有五大客户:12345。这是所有我能想到的条件。

  • 用户1接收到的以任意顺序,然后置于一个支付命令,这个计数
  • 用户2放置在支付订单,然后接收到以任意顺序,这不计数
  • 用户3放置在支付顺序,然后接到自由顺序,然后将其置于一个支付命令,这个不计
  • 用户4接收以任意顺序,这不计数
  • 用户5放置在支付顺序,这不计数

您可以看到我只关心在收到免费订单前没有下过付款订单的用户,然后发出付款订单。我在寻找伯爵的更声明的定义是:

  • 用户下了订单n其中n->total > 0收到订单m,其中m->total == 0m->id < n->id后。没有订单w其中w->total > 0w->id < m->id

一些create table代码:

create table orders (
    id int NOT NULL AUTO_INCREMENT, 
    user int, 
    total decimal(6,2), 
    PRIMARY KEY(id) 
); 

insert into orders (user, total) values 
    (1, 0.00), 
    (1, 57.33), 
    (2, 58.21), 
    (2, 0.00), 
    (3, 26.10), 
    (3, 0.00), 
    (3, 64.94), 
    (4, 0.00), 
    (5, 34.54); 

在这种情况下,预计产量将1

+0

是这条线是否正确? **您可以看到我只关心在收到付款订单前没有下过付款订单的用户,** – 1000111

+0

为了解决您的逻辑问题,我相信我们需要查看每个用户的三个最新ID值以及相应的时间戳。这在MySQL中有点棘手,我认为答案可能需要一些动态SQL。 –

+0

@ 1000111抱歉,在那里犯了一个错字。我已经解决了它,它应该是“谁没有收到免费订单之前下了付费订单”。 – gator

回答

2

简单聚合组合有条件的聚合可以让你找到你正在寻找的用户。

SELECT 
    [user] 
    ,MIN(id) as MinId 
    ,MIN(CASE WHEN total = 0 THEN id END) as MinZeroId 
    ,MIN(CASE WHEN total > 0 THEN id END) as MinPositiveId 
FROM 
    orders 
GROUP BY 
    [user] 
HAVING 
    MIN(id) = MIN(CASE WHEN total = 0 THEN id END) 
    AND MIN(CASE WHEN total > 0 THEN id END) > MIN(CASE WHEN total = 0 THEN id END) 

即最小ID针对最小ID的用户以$ 0总金额进行比较,然后将最小内径为总计> $ 0,则比较的最小内径为$ 0总计。

如果你想要原始记录只需添加一个外部选择来达到它。

SELECT o.* 
FROM 
    (
     SELECT 
      [user] 
     FROM 
      orders 
     GROUP BY 
      [user] 
     HAVING 
      MIN(id) = MIN(CASE WHEN total = 0 THEN id END) 
      AND MIN(CASE WHEN total > 0 THEN id END) > MIN(CASE WHEN total = 0 THEN id END) 
    ) t 
    INNER JOIN orders o 
    ON t.[user] = o.[user] 
0

您需要第一条记录(where子句)总数为零且存在总数不为零的后续记录的记录对(自联接)。 (不必是下一个记录,对吧?)

Select i.User, i.total firstTotal, 
    n.Total firstpaidTotal 
from table i 
    join table n 
    on n.Id > i.id 
     and n.user = i.user 
     and n.total > 0 
where i.total = 0 
    and not exists 
    (Select * from table 
    where user = i.user 
     and id < i.Id)   
+0

不完全是因为他的例子中的用户3。如果0.00然后> 0.00然后0.00应该排除,这不会是您的查询的情况。好的开始:-) –

+0

不存在将排除用户3.它只允许记录,其中id是该用户的最低值,总数= 0 –

0

这可能会解决你的问题:

select a.id from orders a 
join orders b on (a.user = b.user and a.id < b.id and a.total = 0) 
join (select min(id) as id, user from orders group by user) c on (a.user = c.user and a.id = c.id) 

让我知道什么是错的:)

0

另一种可能的解决方案,虽然我个人很喜欢@马特回答了这一个:

SELECT a.user 
FROM orders a 
    -- search first user_line 
    JOIN (
     SELECT b.user, MIN(b.id) first_id 
     FROM orders b 
     GROUP BY b.user 
    ) c ON a.user = c.user AND a.id = c.first_id 
WHERE 
    -- check first line is total=0 
    a.total = 0 
    -- has later lines with total>0 
    AND EXISTS (
     SELECT 'exists' 
     FROM orders c 
     WHERE 
     c.user = a.user 
     AND c.total > 0 
     AND c.id > a.id 
    ) 
相关问题