视图中列上的雪花动态不同计数

问题描述 投票:0回答:1

我有一个包含以下结构和数据的表格。我想根据 WHERE 子句过滤器获取 USER_ID 的不同计数。我可以通过下面的示例查询来实现这一点。

WITH CTE(REPORT,INSTANCE,ROLE,LOGIN_TIME,ISACTIVE,WEB_ACCESS,USER_ID) AS (
SELECT * FROM VALUES 
        ('R1','ABC','ADMIN','2024-04-05 16:00:00','1','YES','U1'),
        ('R1','ABC','DEV','2024-04-04 16:00:00','1','NO','U2'),
        ('R1','ABC','ADMIN','2024-04-03 16:00:00','1','NO','U3'),
        ('R1','ABC','ADMIN','2024-04-07 16:00:00','1','YES','U1'),
        ('R1','ABC','ADMIN','2024-04-09 16:00:00','1','YES','U1'),
        ('R1','ABC','DEV','2024-04-06 16:00:00','1','NO','U2')
)

--SELECT * FROM CTE
--SELECT COUNT( DISTINCT USER_ID) FROM CTE WHERE WEB_ACCESS='NO'; -- Gives 2
--SELECT COUNT( DISTINCT USER_ID) FROM CTE WHERE ROLE='ADMIN';-- gives 2
--SELECT COUNT( DISTINCT USER_ID) FROM CTE WHERE ROLE='ADMIN' and WEB_ACCESS='YES';-- gives 1

但真正的要求是在此表之上为最终用户创建一个视图,并动态生成计数,就像最终用户使用自己的过滤条件查询视图时一样,并且不同的 user_id 计数应填充在不同的列中。

但是,根据 SQL 标准,这无法通过普通视图来实现。只是想从专家那里知道是否有任何可能的方法来呈现 USER_ID 上的总不同计数,同时最终用户可以选择使用 WHERE 子句过滤器在 VIEW 上触发简单的选择。

我不想使用任何UDTF。只需要信息,如果这可以通过任何窗口函数或枢轴或任何其他方式来实现,以将不同计数呈现为最终用户查询视图的视图中的附加字段?

考虑使用以下 DDL 在具有上述共享数据的临时表上创建的视图

CREATE VIEW REPORT_VIEW AS
SELECT
    REPORT,INSTANCE,ROLE,LOGIN_TIME,ISACTIVE,WEB_ACCESS,USER_ID,'Use some logic to get distinct count on USER_ID dynamically' as DISTINCT_USER_ID_COUNT
FROM MY_TABLE

当我如下查询视图 REPORT_VIEW 时,我希望应该为过滤条件填充 DISTINCT_USER_ID_COUNT

SELECT * FROM REPORT_VIEW WHERE WEB_ACCESS='NO';--This should give DISTINCT_USER_ID_COUNT as 2

SELECT * FROM REPORT_VIEW WHERE WEB_ACCESS='YES' AND ROLE='ADMIN';--This should give DISTINCT_USER_ID_COUNT as 1
snowflake-cloud-data-platform window-functions distinct-on
1个回答
0
投票

根据我的理解,这是不可能的。

当您将 COUNT(DISTINCT USER_ID) 定义为视图中的列时,如下所示:

CREATE or replace VIEW REPORT_VIEW AS
SELECT
    REPORT,INSTANCE,ROLE,LOGIN_TIME,ISACTIVE,WEB_ACCESS,USER_ID, 
    count(distinct user_id) over () as DISTINCT_USER_ID_COUNT
FROM test;

视图中使用的任何函数都是针对已定义的过滤器的表定义的。

在这种情况下,当用户运行时:

select * from REPORT_VIEW where  
WEB_ACCESS='YES' AND ROLE='ADMIN';

我们不能下推过滤器,否则会影响原始视图的结果,并会被视为错误结果问题。滤波器必须在窗函数之后应用:

我想用户在从视图中选择时必须手动添加此列:

CREATE or replace VIEW REPORT_VIEW AS
SELECT
    REPORT,INSTANCE,ROLE,LOGIN_TIME,ISACTIVE,WEB_ACCESS,USER_ID
FROM test;

select 
    *, 
    count(distinct user_id) over () as DISTINCT_USER_ID_COUNT
from REPORT_VIEW
where 
    WEB_ACCESS='YES' 
    AND ROLE='ADMIN'
;
© www.soinside.com 2019 - 2024. All rights reserved.