I am using the following code
s_last=catt(substr(s_last,1,length(s_last)-ns),pxs[locx]);
to add some character string to the original one.
This working in cycle and when the size of string reaches 255 process stops, saying the IML procedure can't allocate buffer longer than 256.
At the same time, when I use the sample code
test=rowcat(T(p7s));
show test;
I can see
test 1 row 1 col (character, size 35280) |
So, My question is, how to make use of long character variable, allowing for action like
string_base=catt (string_base, string_add);
The issue you are encountering is because certain Base SAS concatenation functions (CAT, CATS, CATT, CATX, etc) set the length of an uninitialized variable to 200. If the return value from the function exceeds that length, you will get a warning, such as in the following DATA step:
/* some concatenation functions implicitly set the
length that for an unitialized LHS variable to 200 */
data _null_;
s = catt("A", "B"); /* implicitly sets LENGTH s $200 */
/* make a long string */
x1 = "1234567890123456789012345678901234567890"; /* 40 char */
x2 = x1; x3 = x1; x4 = x1; x5 = x1; x6 = x1;
s2 = catt(x1, x2, x3, x4, x5, x6); /* WARNING: RHS does not fit into length=200 */
run;
The log displays
WARNING: In a call to the CATT function, the buffer allocated for the result was not long enough to contain the concatenation of all the arguments. The correct result would contain 240 characters, but the actual result might either be truncated to 200 character(s) or be completely blank, depending on the calling environment. The following note indicates the left-most argument that caused truncation.
If you call one of the "CAT" functions from IML, you will get similar behavior and the WARNING is coming from the Base function.
In the DATA step, you work around this issue by using the LENGTH statement to allocate the left-hand side variable:
length s2 $240;
Because IML uses dynamic allocation for each statement, there is no LENGTH statement in the IML language. Instead, I think you can work around this issue in IML by using the built-in '+' operator, which is the IML version of the concatenation functions. You can combine the '+' operator with the STRIP or TRIM functions if you need to remove blanks. The following IML program reads in long strings and uses the '+' operator to concatenate them. You can see that the resulting strings are longer than 200 characters:
data Have;
/* make long strings */
length s1 s2 $240 x1-x6 $50;
x1 = "1234567890123456789012345678901234567890"; /* 40 char */
x2 = x1; x3 = x1; x4 = x1; x5 = x1; x6 = x1;
s1 = catt(x1, x2, x3, x4, x5, x6);
s2 = s1;
run;
proc iml;
use Have;
read all var {s1 s2 x1 x2 x3 x4 x5 x6};
close;
s = trim(x1) + trim(x2) + trim(x3) +
trim(x4) + trim(x5) + trim(x6);
nlen = nleng(s);
len = length(s);
print nlen len;
s = trim(s1) + trim(s2);
nlen = nleng(s);
len = length(s);
print nlen len;
The issue you are encountering is because certain Base SAS concatenation functions (CAT, CATS, CATT, CATX, etc) set the length of an uninitialized variable to 200. If the return value from the function exceeds that length, you will get a warning, such as in the following DATA step:
/* some concatenation functions implicitly set the
length that for an unitialized LHS variable to 200 */
data _null_;
s = catt("A", "B"); /* implicitly sets LENGTH s $200 */
/* make a long string */
x1 = "1234567890123456789012345678901234567890"; /* 40 char */
x2 = x1; x3 = x1; x4 = x1; x5 = x1; x6 = x1;
s2 = catt(x1, x2, x3, x4, x5, x6); /* WARNING: RHS does not fit into length=200 */
run;
The log displays
WARNING: In a call to the CATT function, the buffer allocated for the result was not long enough to contain the concatenation of all the arguments. The correct result would contain 240 characters, but the actual result might either be truncated to 200 character(s) or be completely blank, depending on the calling environment. The following note indicates the left-most argument that caused truncation.
If you call one of the "CAT" functions from IML, you will get similar behavior and the WARNING is coming from the Base function.
In the DATA step, you work around this issue by using the LENGTH statement to allocate the left-hand side variable:
length s2 $240;
Because IML uses dynamic allocation for each statement, there is no LENGTH statement in the IML language. Instead, I think you can work around this issue in IML by using the built-in '+' operator, which is the IML version of the concatenation functions. You can combine the '+' operator with the STRIP or TRIM functions if you need to remove blanks. The following IML program reads in long strings and uses the '+' operator to concatenate them. You can see that the resulting strings are longer than 200 characters:
data Have;
/* make long strings */
length s1 s2 $240 x1-x6 $50;
x1 = "1234567890123456789012345678901234567890"; /* 40 char */
x2 = x1; x3 = x1; x4 = x1; x5 = x1; x6 = x1;
s1 = catt(x1, x2, x3, x4, x5, x6);
s2 = s1;
run;
proc iml;
use Have;
read all var {s1 s2 x1 x2 x3 x4 x5 x6};
close;
s = trim(x1) + trim(x2) + trim(x3) +
trim(x4) + trim(x5) + trim(x6);
nlen = nleng(s);
len = length(s);
print nlen len;
s = trim(s1) + trim(s2);
nlen = nleng(s);
len = length(s);
print nlen len;
Are you ready for the spotlight? We're accepting content ideas for SAS Innovate 2025 to be held May 6-9 in Orlando, FL. The call is open until September 25. Read more here about why you should contribute and what is in it for you!
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.