2013-04-09 66 views
1

我的代码如下SAS数据步合并/修改2个数据集,但仍保持完整性constrants(PK)的主数据集

data master; 
input id name $ status $; 
datalines; 
1 B b 
2 C c 
3 A a 
;;;; 
run; 

PROC SQL; 
ALTER TABLE master 
ADD PRIMARY KEY (id); 
QUIT; 

data transaction; 
input name $ status $; 
datalines; 
A f 
F f 
E e 
D d 
B z 
C x 
;;;; 
run; 

proc sort data = master; 
by name; 
run; 

proc sort data = transaction; 
by name; 
run; 

我想合并的交易数据集掌握的数据集,并更新来自交易数据集的主值与价值。要做到这一点,我可以使用下面

data have; 
retain _maxID; 
merge have addon; 
by name; 
if id = . then id = _maxID + 1; 
_maxID = max(id, _maxID); 
run; 

代码的结果是这样的

id name status 
3 A  f 
1 B  z 
2 C  x 
4 D  d 
5 E  e 
6 F  f 

然而,主数据集被复位,我失去了主键约束上的id列主数据集。

据我所知,合并,设置和更新命令创建新的数据集,而不是更新当前数据集。

修改语句是唯一一个更新当前数据集,但用上面的代码替换合并语句与修改不起作用。

我可以通过在合并后在主数据集上恢复主约束来解决此问题,但这不是一个好的解决方案。

除此之外还有其他方法吗?感谢您的帮助,并提前致谢。

回答

4

正如您所说,不会创建新数据集的唯一声明是MODIFY,但您可以使用它来实现您的目标。有一个好的SUGI论文使用MODIFY here

这里是您可以使用的代码,我已经设置ID等于当前迭代在这个例子中工作,但我会检查它是适合您的实际目的。

data master; 
modify master transaction; 
by name; 
select (_IORC_); 
    when (%sysrc(_SOK)) replace; 
    when (%sysrc(_DSENMR)) do; 
     id=_n_; 
     output; 
     _error_=0; 
     end; 
    otherwise; 
end; 
run; 

这里有一个类似的回答问题给出了更多的细节。

链接: - similar statement to merge sql in sas

+2

基思我加在你的答案的链接,我会使用修改/ IORC以前回答过类似的问题。这个代码有点不那么通用,但更具描述性,因此可能有用。 – 2013-04-09 23:06:08

+0

感谢您的答案和非常有帮助的Sugi文章。就像Rob的回答中那样,我不知道select可以在数据步骤中使用。再次感谢Keith&Rob。 – 2013-04-10 02:00:34