BookmarkSubscribeRSS Feed
☑ This topic is solved. Need further help from the community? Please sign in and ask a new question.
Pili1100
Obsidian | Level 7

Hi, 

I would like to replace a generic part of a string and replace with value from one variable in another variable. 

Pili1100_0-1668792504941.png

 





/*input*/
DATA input;
LENGTH LIB_TABLES $100;
INPUT LIB_TABLES;
DATALINES;
LIB_A.TABLE_1
LIB_B.TABLE_2
LIB_C.TABLE_3
;

RUN;

/*What I have*/
DATA have;
SET input;
LIB = SCAN( LIB_TABLES, 1, '.');
TABLES = REVERSE(SCAN(REVERSE(LIB_TABLES),1,'.'));
X_have= 'info_tables(LIBNAME=XXX, TABLE=XXX, Table info)';

RUN;



/*Desirable output*/
DATA want; 

LIB_TABLES = 'LIB_A.TABLE_1';
LIB		   = 'LIB_A';
TABLES	   = 'TABLE_1';
X_WANT	   = 'info_tables(LIBNAME=LIB_A,TABLE=TABLE_1, Table info)';
OUTPUT;

	
LIB_TABLES = 'LIB_B.TABLE_2';
LIB		   = 'LIB_B';
TABLES	   = 'TABLE_2';
X_WANT	   = 'info_tables(LIBNAME=LIB_B,TABLE=TABLE_2, Table info)';
OUTPUT;


LIB_TABLES = 'LIB_C.TABLE_3';
LIB		   = 'LIB_C';
TABLES	   = 'TABLE_3';
X_WANT	   = 'info_tables(LIBNAME=LIB_C,TABLE=TABLE_3, Table info)';
OUTPUT;
RUN;	




How should I do it?

Many thanks, 

 

1 ACCEPTED SOLUTION

Accepted Solutions
fja
Lapis Lazuli | Level 10 fja
Lapis Lazuli | Level 10

As you stated that you wanted to _replace_ a certain char group by a variable my suggestion would be using the tranwrd function . ... note the trim(). This was suggested by @Tom in this post

/*input*/ 
DATA input; 
LENGTH LIB_TABLES $100; 
INPUT LIB_TABLES; 
DATALINES; 
LIB_A.TABLE_1 
LIB_B.TABLE_2 
LIB_C.TABLE_3 
; 
RUN; 
 
/*What I have*/ 
DATA have; 
SET input; 
LIB = SCAN( LIB_TABLES, 1, '.'); 
TABLES = REVERSE(SCAN(REVERSE(LIB_TABLES),1,'.')); 
X_have= 'info_tables(LIBNAME=XXX, TABLE=YYY, Table info)'; 
x_want=tranwrd(tranwrd(x_have, "YYY", trim(TABLES)), "XXX", trim(LIB)); 
RUN; 
proc print data=have;

 

fja_0-1668803351806.png

 

View solution in original post

8 REPLIES 8
Cynthia_sas
SAS Super FREQ

Hi:

  You are very close. Using one of the concatenate functions to join your text and your variable values will work. I'd recommend the CATT function, which trims blanks:

Cynthia_sas_0-1668802112714.png

I also simplified your SCAN, since using a -1 tells SCAN to start scanning from the other end of the variable string, which is what your REVERSES were doing.

Cynthia

fja
Lapis Lazuli | Level 10 fja
Lapis Lazuli | Level 10

As you stated that you wanted to _replace_ a certain char group by a variable my suggestion would be using the tranwrd function . ... note the trim(). This was suggested by @Tom in this post

/*input*/ 
DATA input; 
LENGTH LIB_TABLES $100; 
INPUT LIB_TABLES; 
DATALINES; 
LIB_A.TABLE_1 
LIB_B.TABLE_2 
LIB_C.TABLE_3 
; 
RUN; 
 
/*What I have*/ 
DATA have; 
SET input; 
LIB = SCAN( LIB_TABLES, 1, '.'); 
TABLES = REVERSE(SCAN(REVERSE(LIB_TABLES),1,'.')); 
X_have= 'info_tables(LIBNAME=XXX, TABLE=YYY, Table info)'; 
x_want=tranwrd(tranwrd(x_have, "YYY", trim(TABLES)), "XXX", trim(LIB)); 
RUN; 
proc print data=have;

 

fja_0-1668803351806.png

 

Pili1100
Obsidian | Level 7

Thank you for the double-trim. Will come in handy for replacing in a string 😁

Pili1100
Obsidian | Level 7

Hi,

I got so many good solutions from the community. Thank you for helping me. This one works as charm! 🙏

Tom
Super User Tom
Super User

To re-create your example does NOT require replacing any text.

Just GENERATE the text.

DATA input;
  LENGTH LIB_TABLES $100;
  INPUT LIB_TABLES;
DATALINES;
LIB_A.TABLE_1
LIB_B.TABLE_2
LIB_C.TABLE_3
;

data want;
  set input;
  length lib $8 tables $32 x_want $100 ;
  lib=scan(lib_tables,1,'.');
  tables=scan(lib_tables,-1,'.');
  x_want=cats('info_tables(libname=',lib,',table=',tables,',Table info)');
run;

Result

Obs     LIB_TABLES       lib     tables                           x_want

 1     LIB_A.TABLE_1    LIB_A    TABLE_1    info_tables(libname=LIB_A,table=TABLE_1,Table info)
 2     LIB_B.TABLE_2    LIB_B    TABLE_2    info_tables(libname=LIB_B,table=TABLE_2,Table info)
 3     LIB_C.TABLE_3    LIB_C    TABLE_3    info_tables(libname=LIB_C,table=TABLE_3,Table info)

Do you have an example where you actually need to replace text?

Pili1100
Obsidian | Level 7

Thank you for helping me. Another good solution. 😊
Regarding your question, Do you have an example where you actually need to replace text? and the 
reason I need help with this because I was looking for a solution for a makro where I use lib and tables and I wanted to avoid to copy/pase the XXX. 

It can be time consuming when it's 20 tables.  

Patrick
Opal | Level 21

Pretty much the same as Tom already suggested with the one extension to also deal with one level table names.

DATA have;
  LENGTH LIB_TABLES $100;
  INPUT LIB_TABLES;
  DATALINES;
LIB_A.TABLE_1
LIB_B.TABLE_2
LIB_C.TABLE_3
TABLE4
;

data want;
  set have;
  length lib $8 tables $32 x_want $100;
  lib=scan(cats('WORK.',lib_tables),-2,'.');
  tables=scan(lib_tables,-1,'.');
  x_want=cats('info_tables(LIBNAME=',lib,', table=',tables,', Table info)');
run;

 

Patrick_0-1668807737714.png

 

Pili1100
Obsidian | Level 7

Hi, 

Thanks for expanding the solution, having WORK as default. Real nice 👏

 

SAS Innovate 2025: Save the Date

 SAS Innovate 2025 is scheduled for May 6-9 in Orlando, FL. Sign up to be first to learn about the agenda and registration!

Save the date!

How to Concatenate Values

Learn how use the CAT functions in SAS to join values from multiple variables into a single value.

Find more tutorials on the SAS Users YouTube channel.

SAS Training: Just a Click Away

 Ready to level-up your skills? Choose your own adventure.

Browse our catalog!

Discussion stats
  • 8 replies
  • 3840 views
  • 0 likes
  • 5 in conversation