Chapter Contents |
Previous |
Next |
SAS Component Language: Reference |
To illustrate, consider the SAS table WORK.EMPLOYEES, created with the following DATA step program:
data employees; input fname $ 1-9 lname $ 10-18 position $ 19-28 salary 29-34; datalines; Walter Bluerock Developer 36000 Jennifer Godfrey Manager 42000 Kevin Blake Janitor 19000 Ronald Tweety Publicist 29000 ;
The following example reads the WORK.EMPLOYEES table into an SCL list. The outer list is the list in the variable OUTERLIST. Each time through the loop, a new inner list is created. Its identifier is stored in the variable INNERLIST, and INNERLIST is inserted at the end of OUTERLIST.
INIT: /* Open the EMPLOYEES table and */ /* create the SCL list OUTERLIST */ dsid=open('employees'); outerList=makelist(); /* Read the first table row and */ /* find the number of its columns */ rc=fetch(dsid); numcols=attrn(dsid,'NVARS'); /* For each row, make a new INNERLIST */ /* and create and insert the sublists */ do while (rc=0); innerList=makelist(); /* For each column, return the name */ /* and type. Insert a list item of */ /* that name and type into the */ /* row's INNERLIST. */ do i=1 to numcols; name=varname(dsid,i); type=vartype(dsid,i); if type='N' then rc=insertn(innerList,(getvarn (dsid,i)),-1,name); else rc=insertc(innerList,(getvarc (dsid,i)),-1,name); end; /* Insert each INNERLIST as an item */ /* into OUTERLIST and read the next */ /* row of the EMPLOYEES table */ outerList=insertl(outerList,innerList,-1); rc=fetch(dsid); end; /* Close the EMPLOYEES table. Print and */ /* then delete OUTERLIST and its sublists. */ sysrc=close(dsid); call putlist(outerList,'Nested Lists',2); rc=dellist(outerList,'y'); return;
This program produces the following output:
Nested Lists( ( FNAME='Walter' LNAME='Bluerock' POSITION='Developer' SALARY=36000 )[7] [1] ( FNAME='Jennifer' LNAME='Godfrey' POSITION='Manager' SALARY=42000 )[9] [1] ( FNAME='Kevin' LNAME='Blake' POSITION='Janitor' SALARY=19000 )[11] [1] ( FNAME='Ronald' LNAME='Tweety' POSITION='Publicist' SALARY=29000 )[13] [1] )[5] [1] [2]
Limitless Levels of Nesting |
Simulating Multidimensional Arrays with Nested Lists |
array a[2,3] 8 _temporary_; init: listid = makelist(2); lista = setiteml(listid, makelist(3), 1); listb = setiteml(listid, makelist(3), 2); call putlist(listid); do i = 1 to dim(a,1); list=getiteml(listid,i); do j = 1 to dim(a,2); a[i, j] = 10*i + j; put a[i,j]=; rc = setitemn(list,a[i,j], j); end; end; call putlist(listid); return;
This example produces the following output:
((. . . )[7] (. . . )[9] )[5] a[ 1 , 1 ]=11 a[ 1 , 2 ]=12 a[ 1 , 3 ]=13 a[ 2 , 1 ]=21 a[ 2 , 2 ]=22 a[ 2 , 3 ]=23 ((11 12 13 )[7] (21 22 23 )[9] )[5]
Note: Not
all of the program is shown here. You would need to delete these lists before
ending the program. [7], [9], and [5] are the list identifiers that were assigned
when this example was run and may be different each time the example is run.
Saving Nested Lists to SCL Entries |
For example, suppose list A contains list B. When you save list A, you also save list B; you do not need to save list B separately, because list B is already stored in list A. In fact, if you store the lists in two separate SLIST entries and then try to read them back, you do not get the same list structure that you stored originally.
The following example creates two lists, A and B, (with text values in them to identify their contents) and inserts list B into list A. It then saves each list in separate SLIST entries, A.SLIST and B.SLIST. Then, the program creates two more lists, APRIME and BPRIME, reads the two saved SLIST entries into those two lists, and then prints all the list identifiers and list values.
INIT: /* Make lists A and B and insert an item */ /* of text into each list. Then, insert */ /* list B into list A. */ a = makelist(); a = insertc(a, 'This is list A'); b = makelist(); b = insertc(b, 'This is list B'); a = insertl(a, b); /* Save lists A and B into separate */ /* SLIST entries. */ rc=savelist ('CATALOG','SASUSER.LISTS.A.SLIST', A); rc=savelist ('CATALOG','SASUSER.LISTS.B.SLIST', B); /* Make lists APRIME and BPRIME. Fill */ /* APRIME with the contents of A.SLIST */ /* and BPRIME with B.SLIST */ aPrime=makelist(); bPrime=makelist(); rc=fillist ('CATALOG','SASUSER.LISTS.A.SLIST', aPrime); rc=fillist ('CATALOG','SASUSER.LISTS.B.SLIST', bPrime); /* Store list APRIME into list BINA */ bInA = getiteml(aPrime); put a= b= aPrime= bPrime= bInA= ; call putlist(a, 'List A:',0); call putlist(b, 'List B:',0); call putlist(aPrime, "List aPrime:",0); call putlist(bPrime, "List bPrime:",0); /* Delete list A and its sublist B */ /* Delete lists APRIME, BPRIME, and BINA */ rc=dellist(a,'y'); rc=dellist(aPrime); rc=dellist(bPrime); return;
Here is the output:
a=5 b=7 aPrime=9 bPrime=11 bIna=13 List A:(('This is list B )[7] 'This is list A )[5] List B:('This is list B )[7] List aPrime:(('This is list B )[13] 'This is list A )[9] List bPrime:('This is list B )[11]
Note that the sublist B (13) that was read from A.SLIST is not the same as the sublist BPRIME (11) that was read from B.SLIST. That is, A contains B, but B does not contain BPRIME. Therefore, changes made to B are inherently reflected in A, whereas changes to BPRIME are not reflected in APRIME.
Also note that the structures of list A and list APRIME are the same, but the list identifiers are different and do not match any of the list identifiers that were read from B.SLIST.
Note: [5], [7], [9], [11], and [13] are the list identifiers that were assigned
when this example was run and may be different each time the example runs.
Chapter Contents |
Previous |
Next |
Top of Page |
Copyright 1999 by SAS Institute Inc., Cary, NC, USA. All rights reserved.