380 likes | 425 Views
Writing Flexible Codes with the SAS Macro Facility (Chapter in the 7 Little SAS Book) . Animal Science 500 Lecture No. 7 September 21, 2010. SAS Macro Development. SAS Macros used to be utilized by “more advanced” SAS Users Today SAS Macros are being used by more and more people
E N D
Writing Flexible Codes with the SAS Macro Facility(Chapter in the 7 Little SAS Book) Animal Science 500 Lecture No. 7 September 21, 2010
SAS Macro Development • SAS Macros used to be utilized by “more advanced” SAS Users • Today SAS Macros are being used by more and more people • Including beginners • Using existing Macros • Developing your own Macros
General Macro Knowledge • Macros typically take longer to write and debug than a normal SAS program that you might only use a few times • After Macros are developed • Make developing maintaining a “production” program that is used a great deal easier • You can have SAS make a change in one part of your program and have SAS “echo” that throughout the rest of the program • Allows you to write a piece of SAS code and reuse it several times either the same day or days later
The Macro Processor • Compiling “submitting your code” your SAS program is different than when submitting a SAS Macro • Your standard SAS code is submitted and immediately executed • Macros have an additional step • SAS passes the Macro statement to the macro processor which “resolves” your macros that generates standard SAS code • Called meta programming because you write a program that writes a program
Macros and macro variables • SAS macro code has two parts • Macros • Macro variables • Name of the Macro is prefixed with a % • Name of the Macro variables is prefixed with an & • Is like your variable in a data set except it is not associated with a data set and it is always a character variable • Can be • A variable name • A numeral • Any text you want substituted into your program
Macros and macro variables • Macro is a larger piece of program that may contain complex logic • Data • Proc Statements • Macro Statements • %Do • %End • %IF- • %Then/ • %Else
Macros • Macro variable can have different “scopes” • Local – defined within the macro • Global – macro code that is outside of the macro • Use global macro variable anywhere in your program • A local macro variable can only be used inside the macro • Cannot have a global and local macro variable with the same name.
Invoking or Turning on the Macro Processor • Must turn on the MACRO system option in order to use it • Macro is usually on by default • May be turned off – especially true on mainframe computer systems (usually seen in larger businesses, ISU has what some would consider a mainframe but not used by general students • SAS runs faster if it does not have to check and see if there are macros are present • If MACROS are turned off that means SAS does not have to check for them
Invoking or Turning on the Macro Processor • To check and see whether the MACRO option is on use the following SAS code: PROC OPTIONS OPTION = MACRO; RUN; QUIT; • Examine the SAS log • If you see • the option MACRO then the macro processor is turned on • NOMACRO the macro is turned off and you need to specify the MACRO option at invocation or in a configuration file * Specifiying this type of option is system dependent - check your SAS Help and Documentation for your operating system
Substituting Text with Macro Variables • Suppose you have a SAS program that you run once a week • Each time you run the program you have to edit the program so it will select data for the correct range of dates and print the correct dates in the title • Time consuming • Errors frequently happen and then are correct (even time consuming) or you send a report that has errors (bad image)
Substituting Text with Macro Variables • Can use a MACRO variable to insert the correct date; • Using the macros in this manner allows a much less experience person to generate the report – • The person does not have to know SAS code because the changes are made automatically
Substituting Text with Macro Variables • When SAS encounters the name of a macro variable, the macro processor replaces the name with the value of that macro variable. • Simplest way to do this: • Use the Macro called %Let • General form %Let macro-variable-name = value • The macro-variable-name must follow normal SAS rules • 32 characters or less • Start with a letter or _ • Contain only letters, numerals, or underscores.
Substituting Text with Macro Variables • General form %Let macro-variable-name = value • The macro-variable-name must follow normal SAS rules • 32 characters or less • Start with a letter or _ • Contain only letters, numerals, or underscores. • value is the text that is substituted for the macro variable name can be longer than you will ever need 64,000 characters long • The following statements each create a macro variable • % Let iterations = 10; • % Let country = New Zealand;
Substituting Text with Macro Variables • The following statements each create a macro variable • %Let iterations = 10; • %Let country = New Zealand; ** Notice that unlike ordinary assignment statement like infile, value does not need quotation marks (‘ ’ or “ ” ) ** Except for the blanks at the beginning and end, which are trimmed, everything between the equals sign and the semicolon becomes part of the value for that macro variable
Using a Macro Variable • To use a macro variable you just add the & sign (ampersand) and stick the macro variable name wherever you want its value to be substituted. • The macro processor doesn’t look for macros inside single quotation marks to get around this you must use double quotations “ ”. • Do i = 1 to &iterations; • TITLE “Addresses in &country”; • After being resolve by the macro processor, these statements would result in the following: • Do i = 1 to 10; (the 10 came from code on previous slide) • Title “Addresses in New Zealand”;
Adding Parameters to MACROS • Prolog • Macros allow you to use the same set of statements over and over • Parameters are macro variables whose value you set when you invoke a macro
Example • A macro named %QUARTERLYREPORT might start like • %MACRO quarterlyreport (quarter= , salesrep = ); • This macro has two parameters &QUARTER and &SALESREP. • You invoke the macro with the following statement • %quarterlyreport (quarter=3, salesrep=smith)
Example • Suppose the grower often needs a report showing sales to an individual customer and then sort the results. The data contain the customer ID, date of sale, variety of flower, and quantity.
Data -------+--------1--------+--------2--------+--------3 240W 02-07-2000 GINGER 120 356W 02-08-2000 HELICONIA 60 356W 02-08-2000 ANTHURIUM 300 188R 02-11-2000 GINGER 24 188R 02-11-2000 ANTHURIUM 24 240W 02-12-2000 PROTEA 180 356W 02-12-2000 GINGER 240
Program %LET flowertype = Ginger; * Read all the flower sales data and subset with a macro variable; DATA flowersales; INFILE ‘c:\mydocuments\sales\sales.dat’; INPUT CustomerID$4 @6 SaledateMMDDYY10. @17 Variety $9. Quantity; IF Variety = “&flowertype”; Run; Quit; * Invoke a macroto Print the report using a macro variable PROC PRINT DATA = flowersales; FORMAT Saledate WORDDATE18.; TITLE “Sales of &flowertype”; Run; Quit;
Output from Macro Example Sales of Ginger Customer Obs ID SaleDate Variety Quantity 1 240W February 7, 2008 Ginger 120 2 188R February 11, 2008 Ginger 24 3 356W February 12, 2008 Ginger 240
Program * Macro with parameters %MACRO select (customer=, sortvar=); PROC SORT DATA = flowersales OUT = salesout; BY &sortvar; WHERE CustomerID = “&customer”; PROC PRINT DATA = salesout; FORMAT SaleDate WORDDATE18.; TITLE “Orders for Customer Number &customer”; %MEND select;
Output looks like this: Orders for Customer Number 356W 1 Customer OBS ID SalesDate Variety Quantity 1 356W February 8, 2000 Anthurium 300 2 356W February 12, 2000 Ginger 240 3 356W February 8, 2000 Heliconia 60 Orders for Customer Number 240W 2 Customer OBS ID SalesDate Variety Quantity 1 240W February 7, 2000 Ginger 120 2240W February 12, 2000 Protea 180
Creating Modular Code with Macros • If you are writing the same or similar SAS statements over and over consider using a Macro. • You can package a piece of bug free code and use it repeatedly within the same SAS program or in many programs • %Macro and %Mend can be thought of as a sandwich • You can put anything you want
Creating Modular Code with Macros • %Macro and %Mend can be thought of as a sandwich • You can put anything you want • General form is: %MACRO macro-name; (tells SAS it’s the beginning of a Macro) macro-text %MEND macro-name; (tells SAS it’s the end of a Macro) Macro-name is a name you can make up up to 32 characters start with a letter or _ contain only letters, numerals, and underscores
Creating Modular Code with Macros • %Macro and %Mend can be thought of as a sandwich • You can put anything you want • General form is: %MACRO macro-name; (tells SAS it’s the beginning of a Macro) macro-text %MEND macro-name; (tells SAS it’s the end of a Macro) Macro-name is a name you can make up up to 32 characters start with a letter or _ contain only letters, numerals, and underscores
Creating Modular Code with Macros • General form is: %MEND macro-name; • The macro-name in the MEND statement is optional. • Macros will be easier to debug or remove errors if the macro-name is included in the MEND statement • Easier to match MACRO and MEND statements makes the sandwich complete
Macros • Macros can be stored in a central location called an autocall location • Can be used multiple times in different programs by a single programmer • Can be used by multiple programers if they have access to a centrally stored autocall location as long as they have access or permission • Easy way to store macros that might be useful multiple times by a single or multiple users
Macros • Macros can have multiple parameters • Same report but with a different set of data • Example • %Macro macro-name (parameter-1= , parameter-2 , parameter-n= ); Macro-text; %MEND macro-name; Example: A macro named %QUATERLYREPORT might start like this; %Macro quarterlyreport (quarter= , salesrep= ); Could invoke Macro by the following statement; %quarterlyreport (quarter=3,salesrep=Smith);
Macros • Likely will not use macros a great deal with one exception • A macro called PDMIX • Separates means from a Proc Mixed analysis with a user defined separation technique • Duncans, Tukeys, etc. • Assigns letter names to separated means of one or more class variable defined in a Proc Mixed analysis
PDMIX macro PURPOSE: This macro takes two data sets from Proc MIXED (Version 8), created by the DIFFS option on the LSMEANS statement. If an ADJUST= option is used, the pdiffs from this are used, not the unadjusted defaults. The pdiffs are converted to groups, labeled by numbers, and this is merged onto the lsmeans data set. The numbers are converted to letters, and for cases where more than 26 letters are needed, sections of letters are coded. For example, 3 means might have the letters A, (2)A, and (3)A. These 3 means are all different, because although all have the letter A, each A belongs to a different section, identified by (#).
Example use of PDMIX Macro Example of use. Assume the file pdmix800.sas, containing the macro code, is on the a: drive. Then the code below will run MIXED, and run pdmix800 on the lsmeans. MIXED is told not to print the means and pdiffs, using the ODS exclude statement, as pdmix800 does the printing in the more desirable format. Also shown are two optional parameters.
Example use of PDMIX Macro Proc Mixed; class block a b; model y = a b a*b; random block; lsmeansa b a*b/pdiff; odsoutput diffs=ppplsmeans=mmm; odslisting exclude diffslsmeans; run; %include 'a:pdmix800.sas'; %pdmix800(ppp,mmm,alpha=.01,sort=yes);