简体   繁体   English

在SAS EG proc SQL中循环数据集

[英]Loop for dataset in SAS EG proc SQL

I am new in SAS EG and I want to know how to append numbers through looping based on three column values in SAS EG. 我是SAS EG的新手,我想知道如何通过基于SAS EG中三列值的循环来追加数字。 For example. 例如。

Column0 Column1 Column2 Level (desired result) 1A AA 0 1A 123AA AA 1 1A 234AA 123AA 2 2B BB 0 2B 123BB BB 1 2B 234BB BB 1 2B 345BB 123BB 2 2B 456BB 345BB 3 Column0 Column1 Column2 Level(期望的结果)1A AA 0 1A 123AA AA 1 1A 234AA 123AA 2 2B BB 0 2B 123BB BB 1 2B 234BB BB 1 2B 345BB 123BB 2 2B 456BB 345BB 3

Would like to know if there's any way I can do a vlookup on the same table and add new column to store the result data in the same table? 想知道是否有任何方法可以在同一个表上执行vlookup并添加新列以将结果数据存储在同一个表中?

SQL does not know about the order of the rows as stored on disk, and your data has no additional column for values that could direct a SORTED BY. SQL不知道存储在磁盘上的行的顺序,并且您的数据没有可用于指向SORTED BY的值的附加列。

The DATA step offers a simpler approach where the sequence of rows is 'as read'. DATA步骤提供了一种更简单的方法,其中行序列为“读取”。 A hash object keyed by column1 can maintain the value of level from prior rows and column2 can be used as the key value for lookup. 由column1键入的哈希对象可以保持先前行的级别值,而column2可以用作查找的键值。

For example: 例如:

data have;
infile datalines missover;
input
Column0 $ Column1 $ Column2 $; datalines;
1A        AA             
1A        123AA     AA   
1A        234AA     123AA
2B        BB             
2B        123BB     BB   
2B        234BB     BB   
2B        345BB     123BB
2B        456BB     345BB
run;

data want;

  set have;
  by column0;

  if _n_ = 1  then do;
    declare hash lookup();
    lookup.defineKey('column1');
    lookup.defineData('level');
    lookup.defineDone();
  end;

  if first.column0 then
    lookup.Clear();

  if (lookup.find(key:column2) ne 0) then
    level = 0;
  else
    level + 1;

  lookup.add();
run;

Note: The above approach may need adjustment to work in VIYA. 注意:上述方法可能需要调整才能在VIYA中使用。

To do the same in SQL requires multiple steps. 在SQL中执行相同操作需要多个步骤。 One step per level being computed (or discovered) for appropriate children. 为适当的孩子计算(或发现)每个级别一步。

proc sql;
  create table level0 as
  select child.*, 0 as level from have as child
  where child.column2 is null;

  %put &=SQLOBS;

  create table level1 as
  select child.*, 1 as level from level0 as parent join have as child
  on parent.column0 = child.column0 and child.column2 = parent.column1;

  %put &=SQLOBS;

  create table level2 as
  select child.*, 2 as level from level1 as parent join have as child
  on parent.column0 = child.column0 and child.column2 = parent.column1;

  %put &=SQLOBS;

  create table level3 as
  select child.*, 3 as level from level2 as parent join have as child
  on parent.column0 = child.column0 and child.column2 = parent.column1;

  %put &=SQLOBS;

  create table level4 as
  select child.*, 4 as level from level3 as parent join have as child
  on parent.column0 = child.column0 and child.column2 = parent.column1;

  %put &=SQLOBS; * 0 obs, so no more children needing parentage found;

  create table want as
  select * from level0 union 
  select * from level1 union
  select * from level2 union
  select * from level3 
  order by column0, level
  ;

A generic approach would have to loop until SQLOBS is 0 通用方法必须循环,直到SQLOBS为0

  create table level&LOOPINDEX as
  select child.*, &LOOPINDEX as level 
  from level&LOOPINDEX_MINUS_1 as parent 
  join have as child
  on parent.column0 = child.column0 and child.column2 = parent.column1;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM