簡體   English   中英

是否有 SQL 僅顯示所有列的前一行更改的值?

[英]Is there an SQL to show only the value that got changed from the previous row for all columns?

我有一個歷史表,其中包含所有值,如果值發生更改,那么它將是一個新行。 這是例子

name    mod_date                create_user_id  is_active   other_column
name1   2020-01-06 22:06:58+00  1               1           value1
name1   2020-01-06 22:07:01+00  2               1           value2
name2   2020-01-06 22:07:27+00  1               1           value2

然后在查詢之后我希望結果是這樣的

name    mod_date                create_user_id is_active other_column
name1   2020-01-06 22:06:58+00  1              1         value1
        2020-01-06 22:07:01+00  2                        value2
name2   2020-01-06 22:07:27+00  1       

我想說明的一點是更容易檢查時間戳后更改了哪個值。 第一行將始終存在,因為它是默認的。 然后下一行只顯示create_user_idother_column因為它從1更改為2 ,將value1更改為value2

is_active將是空的,因為它從未改變

我讀過lagpartition但它似乎只適用於一列,因為我想檢查每一列

這是我的例子

select name
from (select h.*,
    lag(name) over(partition by h.id order by h.mod_date) lag_name
from history h
) h
where name <> lag_name;

如果您沒有太多列,那么您可以單獨為每列的先前值使用滯后。 您還可以為窗口使用別名,因為您將在同一窗口運行它以使查詢易於閱讀。

select name
from (select h.*,
    lag(name) over main_window as lag_name,
    lag(create_user_id) over main_window as prev_user_id,
    lag(is_active) over main_window as prev_is_active,
    lag(other_column) over main_window as prev_other_column
from history h
window main_window as (partition by h.id order by h.mod_date)
) h
where name <> lag_name
or create_user_id <> prev_user_id
or is_active <> prev_is_active
or other_column <> prev_other_column

對於每一列,使用類似的表達式

CASE WHEN lag(col) OVER (ORDER BY mod_date) IS DISTINCT FROM col THEN col END

如果相鄰行的列值相同,則將產生 NULL。

您將不得不列出所有列,但我認為最簡單的表達式可能是:

select nullif(name, lag(name) over (order by mod_date)) as name,
       mod_date,
       nullif(create_user_id, lag(create_user_id) over (order by mod_date)) as create_user_id,
       nullif(is_active, lag(is_active) over (order by mod_date)) as is_active,
       nullif(other_column, lag(name) over (order by mod_date)) as other_column
from t
order by mod_date;

您可以使用information_schema.columns為任何審計表構造查詢以獲取表中的所有列。

這假設列值不是NULL —— 如果它們是,那么你的結果無論如何都是不明確的。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM