I want to use indexing to change the contents of a SAS/IML sublist. I do not know if I am making syntax errors or if SAS/IML does not do what I want it to do because I am exceeding the product's design specs. Here is my code example:
proc iml ;
package load ListUtil ;
charVec = { 'abcde' 'fgh' 'ijklmn' } ; /* define 1x3 character vector */
L_char = [ #'charVec'=charVec ] ; /* define list comprising one item of 1x3 character entries */
call struct( L_char ) ;
temp = L_char$'charVec' ; /* create 1x3 character matrix from list item */
call struct( temp ) ;
do i = 1 to ncol( temp ) ;
print i 'temp[' i ']=' ( temp[ i ] ) ; /* print contents of temp as individual entries to demonstrate scalar addressing */
end ;
L_char =[ #'temp1'=temp ] ; /* create new list comprising one item of 1x3 character entries */
call struct( L_char ) ;
L_char1 = L_char$'temp1'[ { 3 2 1 } ] ; /* create new list of reversed character entries */
L_char1$('temp'[ 2 ]) = 'middle string' ; /* attempt to change contents of subitem using indexing */
call struct( L_char1 ) ;
quit
The IML interpreter generates an error when I try to index into the L_char1$'charVec' sublist:
ERROR: (execution) Invalid subscript or subscript out of range.
I do not know how to create the correct syntax to change an entry in the sublist temp1 in the list L_char1. Am I trying to do something that is not possible within IML as currently defined, or do I merely not understand the syntactic niceties?
TIA,
Ross Bettinger
Pay attention to the types of the variables. You wrote
L_char1 = L_char$'temp1'[ { 3 2 1 } ] ; /* create new list of reversed character entries */
but actually L_char1 is a character vector (so shouldn't have an L_ prefix). Thus, you can't use the $ operator on it.
The next line has several errors. There is no named item 'temp'. You can't replace part of an item; you can only replace the item. You are attempting to assign a value that is longer than the character vector can hold.
Assuming your goal is to change the second element of L_char$'temp1', you can do it like this:
c = L_char$'temp1'; /* extract item */
print (nleng(c)); /* length is only 6 */
c[2] = 'middle string' ; /* change value (it will be truncated at 6 characters) */
L_char$'temp1' = c; /* update item */
call struct( L_char ) ;
Pay attention to the types of the variables. You wrote
L_char1 = L_char$'temp1'[ { 3 2 1 } ] ; /* create new list of reversed character entries */
but actually L_char1 is a character vector (so shouldn't have an L_ prefix). Thus, you can't use the $ operator on it.
The next line has several errors. There is no named item 'temp'. You can't replace part of an item; you can only replace the item. You are attempting to assign a value that is longer than the character vector can hold.
Assuming your goal is to change the second element of L_char$'temp1', you can do it like this:
c = L_char$'temp1'; /* extract item */
print (nleng(c)); /* length is only 6 */
c[2] = 'middle string' ; /* change value (it will be truncated at 6 characters) */
L_char$'temp1' = c; /* update item */
call struct( L_char ) ;
Join us for SAS Innovate 2025, our biggest and most exciting global event of the year, in Orlando, FL, from May 6-9. Sign up by March 14 for just $795.
Learn how to run multiple linear regression models with and without interactions, presented by SAS user Alex Chaplin.
Find more tutorials on the SAS Users YouTube channel.