gpt4 book ai didi

mysql - 复杂的SQL查询建议

转载 作者:行者123 更新时间:2023-11-29 03:03:39 26 4
gpt4 key购买 nike

我有三个表,架构如下:

表:应用

| ID (bigint) | USERID (Bigint)|      START_TIME (datetime) | 
-------------------------------------------------------------
| 1 | 13 | 2013-05-03 04:42:55 |
| 2 | 13 | 2013-05-12 06:22:45 |
| 3 | 13 | 2013-06-12 08:44:24 |
| 4 | 13 | 2013-06-24 04:20:56 |
| 5 | 13 | 2013-06-26 08:20:26 |
| 6 | 13 | 2013-09-12 05:48:27 |

表:主机

| ID (bigint) | APPID (Bigint)|         DEVICE_ID (Bigint)  | 
-------------------------------------------------------------
| 1 | 1 | 1 |
| 2 | 2 | 1 |
| 3 | 1 | 1 |
| 4 | 3 | 3 |
| 5 | 1 | 4 |
| 6 | 2 | 3 |

表:用法

| ID (bigint) | APPID (Bigint)|             HOSTID (Bigint) |   Factor (varchar)    |  
-------------------------------------------------------------------------------------
| 1 | 1 | 1 | Low |
| 2 | 1 | 3 | High |
| 3 | 2 | 2 | Low |
| 4 | 3 | 4 | Medium |
| 5 | 1 | 5 | Low |
| 6 | 2 | 2 | Medium |

现在,如果 put 是 userid,我想获取过去 6 个月每个“因素”月份的每个月(所有应用程序)表格行的行数。。 p>

如果 DEVICE_ID 在一个月内出现不止一次(基于 START_TIME,基于加入应用程序和主机),计算计数时仅考虑最新行的使用情况(基于应用程序、主机和使用情况的组合)。

上述示例查询的示例输出应为:(对于输入用户 id=13)

| MONTH       | USAGE_COUNT   |               FACTOR        | 
-------------------------------------------------------------
| 5 | 0 | High |
| 6 | 0 | High |
| 7 | 0 | High |
| 8 | 0 | High |
| 9 | 0 | High |
| 10 | 0 | High |
| 5 | 2 | Low |
| 6 | 0 | Low |
| 7 | 0 | Low |
| 8 | 0 | Low |
| 9 | 0 | Low |
| 10 | 0 | Low |
| 5 | 1 | Medium |
| 6 | 1 | Medium |
| 7 | 0 | Medium |
| 8 | 0 | Medium |
| 9 | 0 | Medium |
| 10 | 0 | Medium |

这是如何计算的?

  1. 2013 年 5 月 (05-2013),表 Apps 中有两个 App
  2. 在表 Hosts 中,这些应用与 device_id 的 1,1,1,4,3 相关联
  3. 本月 (05-2013) 对于 device_id=1,start_time 的最新值为:2013-05-12 06:22:45(来自表 hosts、apps),因此在表 Usage 中,查找组合appid=2&hostid=2 其中有两行,其中一行的因子为 Low,另一行为 Medium,
  4. 本月 (05-2013) 对于 device_id=4,按照相同的程序我们得到一个条目,即 0 Low
  5. 同样计算所有值。

要通过查询获取最近 6 个月的信息,我尝试使用以下方法获取它:

SELECT MONTH(DATE_ADD(NOW(), INTERVAL aInt MONTH)) AS aMonth
FROM
(
SELECT 0 AS aInt UNION SELECT -1 UNION SELECT -2 UNION SELECT -3 UNION SELECT -4 UNION SELECT -5
)

请检查 sqlfiddle:http://sqlfiddle.com/#!2/55fc2

最佳答案

因为您正在进行的计算涉及多次相同的连接,所以我首先创建一个 View 。

CREATE VIEW `app_host_usage`
AS
SELECT a.id "appid", h.id "hostid", u.id "usageid",
a.userid, a.start_time, h.device_id, u.factor
FROM apps a
LEFT OUTER JOIN hosts h ON h.appid = a.id
LEFT OUTER JOIN `usage` u ON u.appid = a.id AND u.hostid = h.id
WHERE a.start_time > DATE_ADD(NOW(), INTERVAL -7 MONTH)

存在 WHERE 条件是因为我假设您不希望将 2005 年 7 月和 2006 年 7 月归为同一计数。

有了那个 View ,查询就变成了

SELECT months.Month, COUNT(DISTINCT device_id), factors.factor
FROM
(
-- Get the last six months
SELECT (MONTH(NOW()) + aInt + 11) % 12 + 1 "Month" FROM
(SELECT 0 AS aInt UNION SELECT -1 UNION SELECT -2 UNION SELECT -3 UNION SELECT -4 UNION SELECT -5) LastSix
) months
JOIN
(
-- Get all known factors
SELECT DISTINCT factor FROM `usage`
) factors
LEFT OUTER JOIN
(
-- Get factors for each device...
SELECT
MONTH(start_time) "Month",
device_id,
factor
FROM app_host_usage a
WHERE userid=13
AND start_time IN (
-- ...where the corresponding usage row is connected
-- to an app row with the highest start time of the
-- month for that device.
SELECT MAX(start_time)
FROM app_host_usage a2
WHERE a2.device_id = a.device_id
GROUP BY MONTH(start_time)
)
GROUP BY MONTH(start_time), device_id, factor

) usageids ON usageids.Month = months.Month
AND usageids.factor = factors.factor
GROUP BY factors.factor, months.Month
ORDER BY factors.factor, months.Month

这非常复杂,但我已尝试通过评论解释每个部分的作用。请参阅此 sqlfiddle:http://sqlfiddle.com/#!2/5c871/1/0

关于mysql - 复杂的SQL查询建议,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19213871/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com