【问题标题】:Join / Merge two tables removing new duplicates [PROC SQL in SAS]加入/合并两个表以删除新的重复项 [PROC SQL in SAS]
【发布时间】:2016-03-12 22:58:37
【问题描述】:

论坛上有人问过类似的问题,但我似乎有一个独特的问题。我不确定这是因为我没有唯一的 ID 还是因为我的 KEY 是我的实际数据。希望大家帮忙。

我正在尝试合并具有相同列结构的两个表(旧表和新表)。

我想保留旧表中的所有值,并仅将新表中的新变量附加到组合表中。两个表中存在的任何键都应采用旧表的值。

OLD TABLE
Key | Points
AAA | 1
BBB | 2
CCC | 3

NEW TABLE
Key | Points
AAA | 2
BBB | 5
CCC | 8
DDD | 6

Combined TABLE
Key | Points
AAA | 1
BBB | 2
CCC | 3
DDD | 6

我觉得我想要实现的是相当于这个的维恩图:

Venn diagram

...但无论出于何种原因,我都没有使用此代码获得预期的效果:

CREATE TABLE Combined
SELECT * FROM Old as A
FULL OUTER JOIN New as B ON A.Key=B.Key
WHERE A.Key IS NULL OR B.Key IS NULL;

【问题讨论】:

  • 我在搜索 SO 的同时解决了这个问题,但似乎无法找到有效的解决方案?
  • SELECT isnull(old.Key, new.Key) Key, isnull(old.Points, new.Points) Points FROM Old FULL OUTER JOIN New ON old.Key = new.Key
  • 看起来 SAS 有严重的限制 - 它也不会将 ISNULL 识别为函数:/

标签: sql join merge sas proc-sql


【解决方案1】:

对数据集进行排序

proc sort data=old; 
    by key; 
run;
proc sort data=new; 
    by key; 
run;

用by将它们与数据集结合,如果匹配则只输出第一个key

data combined;
set 
    old
    new;
by key;
if first.key then output;
run;

【讨论】:

  • 我最终只使用了 SAS 而不是 PROC SQL。你的实现比我的要复杂得多!谢谢。
  • 没问题 :) 请注意,此代码将删除所有重复的键值,即使它们仅在新表中。组合表将仅存储所述键的第一次出现。
【解决方案2】:

这可能会对你有所帮助。

SELECT B.[Key], MIN(CASE WHEN A.[Key] = B.[Key] THEN A.Points ELSE B.Points END) AS 'Points' FROM OldTable A CROSS APPLY NewTable B GROUP BY B.[Key]

【讨论】:

  • 值得一提的是我在SAS中使用的是Proc SQL函数,它不识别Cross Apply函数
  • 确保要显示的点是用于每个键的第一个点。这是你想要达到的目标吗?
  • 您使用的 SQL 版本是什么?
  • 如果 CROSS APPLY 不起作用,您可以尝试使用相同的输出 SELECT B.[Key], MIN(CASE WHEN A.[Key] = B.[Key] THEN A.Points ELSE B. Points END) AS 'Points' FROM OldTable A, NewTable B GROUP BY B.[Key]
  • 我现在正在测试您的代码 Tonton。我仍然想知道您的 MIN() 函数是否会从任一键中获取两个值中较小的一个?分配的较新点可能不会更大。
【解决方案3】:

只要两个表中的 key 没有重复值:

SELECT COALESCE(a.key,b.key) AS key, COALESCE(a.points,b.points) AS points
  FROM old a FULL OUTER JOIN new b ON a.key EQ b.key

如果第一个值没有丢失,Coalesce 返回第一个值,否则返回第二个值。

【讨论】:

  • 不幸的是,存在重复的键,我们希望保留旧版本中的值。
  • 或者你的意思是每个单独的表本身都有重复项?
  • 我的意思是源表中的重复项。只要给定表中的所有键值都是唯一的,并且点永远不会为空/缺失,上述方法就可以工作。
【解决方案4】:

如果您在任一表中都没有重复键,则数据步骤中的简单 update 语句将完成这项工作。您只需要确保NEW_TABLE 是列表中的第一个,因此OLD_TABLE 中的值将替换键匹配的值。任何一个表唯一的键都会自动输出。

您的数据需要按 Key 排序,如您的示例所示。

data OLD_TABLE;
input Key $ Points;
datalines;
AAA 1
BBB 2
CCC 3
;
run;

data NEW_TABLE;
input Key $ Points;
datalines;
AAA 2
BBB 5
CCC 8
DDD 6
;
run;

data want;
update new_table old_table;
by key;
run;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2015-11-29
    • 2017-06-05
    • 1970-01-01
    • 2010-11-22
    • 1970-01-01
    • 2020-08-04
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多