Query 2 COUNTS 用 GROUP BY 语句出问题
Query 2 COUNTS with a GROUP BY statement trouble
我正在尝试查询 table 中每个组的注册用户和注册用户的计数。
但是,我不断收到重复的群组名称、注册和登记。我需要它只是唯一的组名,在其各自的列中有计数。我是新手,我已经为此纠结了 3 天。任何帮助将不胜感激。下面是我最接近的,但仍然得到重复的组名。
WITH CTE_GROUP as (
SELECT DISTINCT [GROUP] AS GROUPS
FROM TABLE1
WHERE AUTH_PAGE = 'X' AND CAST(CreationDate AS DATE) >= '2022-04-01' AND CAST(CreationDate AS DATE) < '2022-05-01' AND EMAIL IS NOT NULL AND EMAIL <> '' AND EMAIL NOT LIKE '%@company.com' OR CAST(CreationDate AS DATE) >= '2022-04-01' AND CAST(CreationDate AS DATE) < '2022-05-01' AND EMAIL IS NOT NULL AND EMAIL <> '' AND EMAIL NOT LIKE '%@company.com'
GROUP BY [GROUP]
),
CTE_REGISTERED as (
SELECT [GROUP], COUNT (*) AS REGISTERED
FROM TABLE1
WHERE CAST(CreationDate AS DATE) >= '2022-04-01' AND CAST(CreationDate AS DATE) < '2022-05-01' AND EMAIL IS NOT NULL AND EMAIL <> '' AND EMAIL NOT LIKE '%@company.com'
GROUP BY [GROUP]
),
CTE_ENROLLED as (
SELECT [GROUP], COUNT (*) AS ENROLLED
FROM TABLE1
WHERE AUTH_PAGE = 'X' AND CAST(CreationDate AS DATE) >= '2022-04-01' AND CAST(CreationDate AS DATE) < '2022-05-01' AND EMAIL IS NOT NULL AND EMAIL <> '' AND EMAIL NOT LIKE '%@company.com'
GROUP BY [GROUP]
)
SELECT DISTINCT GROUPS, REGISTERED, ENROLLED
FROM CTE_GROUP, CTE_REGISTERED, CTE_ENROLLED
我的结果是这样的
GROUPS REGISTERED ENROLLED
CompanyA 3 2
CompanyB 3 3
CompanyA 3 2
CompanyB 3 3
我要找的结果应该是
GROUPS REGISTERED ENROLLED
CompanyA 3 2
CompanyB 3 3
谢谢
您的结果集基本上是一个 CROSS JOIN
,因为您在三个 CTE 之间没有 JOIN
条件。
试试这个:
SELECT
*
FROM
CTE_GROUP AS [Groups]
INNER JOIN CTE_Registered AS [Registered] ON [Groups].[GROUPS] = [Registered].[GROUP]
INNER JOIN CTE_ENROLLED AS [Enrolled] ON [Groups].[GROUPS] = [Enrolled].[GROUP]
一般来说,当你处理来自多个表的数据时(无论它们是实际的物理表、视图,还是in-memory表),你需要让数据库引擎知道这些数据是如何相关的.为此,您可以创建关系(使用主键和外键),并使用 JOIN
条件在查询中指示引擎。表可以通过多个字段关联,在这种情况下,您可以在 JOIN
条件中将它们串在一起,就像 WHERE
子句一样。
请注意,有多种方法可以执行 JOIN
,结果将取决于您是否使用了正确的类型。在我提供的示例查询中,我使用了 INNER JOIN
,它确保您只返回包含在 JOIN
.
中的两个表中都存在的结果
我相信您需要在单个查询中使用“条件聚合”:
SELECT
[group]
, count(*) AS registered
, count(CASE WHEN AUTH_PAGE = 'X' THEN 1 END) AS enrolled
FROM table1
WHERE CreationDate >= '20220401'
AND CreationDate < '20220501'
AND EMAIL NOT LIKE '%@company.com'
GROUP BY
[group]
;
本质上,您在聚合函数中使用 case expression
,例如 count()
,这样您的计数将继承通过 case expression
定义的“条件”。
另请注意,您无需将 [CreationDate] 强制转换为“日期”即可使 where 子句谓词起作用。所有 date/time 相关的数据类型都可以与日期文字进行比较。此外,在 SQL 服务器中,“最安全”的日期文字只是 YYYYMMDD 格式。
我正在尝试查询 table 中每个组的注册用户和注册用户的计数。
但是,我不断收到重复的群组名称、注册和登记。我需要它只是唯一的组名,在其各自的列中有计数。我是新手,我已经为此纠结了 3 天。任何帮助将不胜感激。下面是我最接近的,但仍然得到重复的组名。
WITH CTE_GROUP as (
SELECT DISTINCT [GROUP] AS GROUPS
FROM TABLE1
WHERE AUTH_PAGE = 'X' AND CAST(CreationDate AS DATE) >= '2022-04-01' AND CAST(CreationDate AS DATE) < '2022-05-01' AND EMAIL IS NOT NULL AND EMAIL <> '' AND EMAIL NOT LIKE '%@company.com' OR CAST(CreationDate AS DATE) >= '2022-04-01' AND CAST(CreationDate AS DATE) < '2022-05-01' AND EMAIL IS NOT NULL AND EMAIL <> '' AND EMAIL NOT LIKE '%@company.com'
GROUP BY [GROUP]
),
CTE_REGISTERED as (
SELECT [GROUP], COUNT (*) AS REGISTERED
FROM TABLE1
WHERE CAST(CreationDate AS DATE) >= '2022-04-01' AND CAST(CreationDate AS DATE) < '2022-05-01' AND EMAIL IS NOT NULL AND EMAIL <> '' AND EMAIL NOT LIKE '%@company.com'
GROUP BY [GROUP]
),
CTE_ENROLLED as (
SELECT [GROUP], COUNT (*) AS ENROLLED
FROM TABLE1
WHERE AUTH_PAGE = 'X' AND CAST(CreationDate AS DATE) >= '2022-04-01' AND CAST(CreationDate AS DATE) < '2022-05-01' AND EMAIL IS NOT NULL AND EMAIL <> '' AND EMAIL NOT LIKE '%@company.com'
GROUP BY [GROUP]
)
SELECT DISTINCT GROUPS, REGISTERED, ENROLLED
FROM CTE_GROUP, CTE_REGISTERED, CTE_ENROLLED
我的结果是这样的
GROUPS REGISTERED ENROLLED
CompanyA 3 2
CompanyB 3 3
CompanyA 3 2
CompanyB 3 3
我要找的结果应该是
GROUPS REGISTERED ENROLLED
CompanyA 3 2
CompanyB 3 3
谢谢
您的结果集基本上是一个 CROSS JOIN
,因为您在三个 CTE 之间没有 JOIN
条件。
试试这个:
SELECT
*
FROM
CTE_GROUP AS [Groups]
INNER JOIN CTE_Registered AS [Registered] ON [Groups].[GROUPS] = [Registered].[GROUP]
INNER JOIN CTE_ENROLLED AS [Enrolled] ON [Groups].[GROUPS] = [Enrolled].[GROUP]
一般来说,当你处理来自多个表的数据时(无论它们是实际的物理表、视图,还是in-memory表),你需要让数据库引擎知道这些数据是如何相关的.为此,您可以创建关系(使用主键和外键),并使用 JOIN
条件在查询中指示引擎。表可以通过多个字段关联,在这种情况下,您可以在 JOIN
条件中将它们串在一起,就像 WHERE
子句一样。
请注意,有多种方法可以执行 JOIN
,结果将取决于您是否使用了正确的类型。在我提供的示例查询中,我使用了 INNER JOIN
,它确保您只返回包含在 JOIN
.
我相信您需要在单个查询中使用“条件聚合”:
SELECT
[group]
, count(*) AS registered
, count(CASE WHEN AUTH_PAGE = 'X' THEN 1 END) AS enrolled
FROM table1
WHERE CreationDate >= '20220401'
AND CreationDate < '20220501'
AND EMAIL NOT LIKE '%@company.com'
GROUP BY
[group]
;
本质上,您在聚合函数中使用 case expression
,例如 count()
,这样您的计数将继承通过 case expression
定义的“条件”。
另请注意,您无需将 [CreationDate] 强制转换为“日期”即可使 where 子句谓词起作用。所有 date/time 相关的数据类型都可以与日期文字进行比较。此外,在 SQL 服务器中,“最安全”的日期文字只是 YYYYMMDD 格式。