Friday, February 22, 2013

SAS: Floating Point Exception in PROC GLMSELECT

We encountered a strange error in PROC GLMSELECT

      ERROR: Invalid operation.
      ERROR: Termination due to Floating Point Exception.

We asked SAS Support for help.  I sent them the program and a trivial data set with just three records which would cause this exception when processed.

What was confusing is we have run this code many, many times before.

Well, SAS' recommended fix was to add this statement inside PROC GLMSELECT:

      performance buildsscp=full;

And it worked...



Unix: How much memory is on this machine?

To see how much memory is on a machine running Unix, issue the "top" command from the command line (Putty, etc.)  You'll see the answer on the third line of display, for example Mem: 32844876k total.  Type q to quit the top command.

Tuesday, February 19, 2013

SAS: Getting to know the data

Next time I have to familiarize myself with a crap load of client data for a new project, I am going to do something like this...

libname desktop "C:\Users\Owner\Desktop";
proc contents data=desktop._all_ out=Work.Contents noprint;
run;

data Work.Contents
 (keep = Libname Memname Name Type Length Format);
set Work.Contents;
run;


...and export the results to Excel so I can filter easily.



Friday, February 15, 2013

Excellent command line reference: www.ss64.com

Excellent command line reference (I used it for some batch file stuff but there is so much more available.)

http://ss64.com/



Tuesday, February 12, 2013

SAS: Suppress PROC output

I need to run a SAS PROC repeatedly.  I will append the results to a file.  So I want to suppress the PROC's normal printed output:

    * suppress lengthy proc outputs;
    filename junk dummy;
    proc printto print=junk;
    run;

    * do your thing here ;


    * restart print;
    proc printto;
    run;




Thursday, February 7, 2013

SAS: Reading the directory

I have to import a file which will be created everyday.  IT gets moved to the server automatically by another process.  It has date and time in the filename.  I won't know the time.  How can I import this?  Well, I need to determine the full filename, and to do so I will need to query the directory.

Here's a link to the article which I used:  http://support.sas.com/kb/41/880.html

Here's a subset of my code (which must run on Windows and Linux):

* Get todays date as a macro variable in MMDDYYYY format;

data _null_;
today = input("&SYSDATE9", anydtdte10.);
mmddyyyy = put(today, mmddyyn8.);
call symput("MMDDYYYY", mmddyyyy);
run;

%put &MMDDYYYY;

%macro op;
%if (&SYSSCP = WIN) %then %do;
    filename DIRLIST pipe "dir &SOURCE_LIB.&STARTS_WITH.&MMDDYYYY.*.csv " ;
%end;
%else %do;
    filename DIRLIST pipe "ls &SOURCE_LIB.&STARTS_WITH.&MMDDYYYY.*.csv" ;
%end;
%mend;

%op;

* I do not know full filename.  Has mmddyyyy followed by a six digit. ;
* number, followed by .csv.  I need to isolate that six digit number. ;
* See http://support.sas.com/kb/41/880.html ;
data dirlist ;                                              
infile dirlist lrecl=200 truncover;                         
input line $200.; 
where_is_dot_csv = index(line, ".csv");
if (where_is_dot_csv = 0) then delete;
where_is_date = index(line, "&MMDDYYYY");
number = substr(line, (where_is_date + 8), where_is_dot_csv - (where_is_date + 8));
put number=;
call symput("NUMBER", trim(left(number)));
run;

%let FULLNAME = &SOURCE_LIB.&STARTS_WITH.&MMDDYYYY.&NUMBER..csv;

proc import datafile="&FULLNAME"
    out=Work.Imported
    dbms=csv
    replace;
    getnames=yes
    ;
run;



Friday, February 1, 2013

SAS: Process six months of data at a time

Due to space constraints, I need to process six months of data at a time.  Here's how I will do it:

* How I will process six months of data at a time ;

* These will come from global constants file ;
%let GLBL_EARLIEST_DATE_TO_IMPORT = '01Jan2011'd;
%let GLBL_LATEST_DATE_TO_IMPORT = '01Jan2014'd;

* Show what we got ;
%put GLBL_EARLIEST_DATE_TO_IMPORT = %sysfunc(putn(&GLBL_EARLIEST_DATE_TO_IMPORT, yymmddn8.));
%put GLBL_LATEST_DATE_TO_IMPORT = %sysfunc(putn(&GLBL_LATEST_DATE_TO_IMPORT, yymmddn8.));

* Here is the start of the macro definition ;

%macro doit;

* Starting date is determined by global macro constant ;
%let FIRST_DAY = %sysevalf(&GLBL_EARLIEST_DATE_TO_IMPORT);
%put FIRST_DAY = %sysfunc(putn(&FIRST_DAY, yymmddn8.));

* Will count number of iterations. Count will be used in filename of temp output ;
%let ITERATIONS = 0;

%do %while (&FIRST_DAY <= %sysevalf(&GLBL_LATEST_DATE_TO_IMPORT));

%let ITERATIONS = %sysevalf(&ITERATIONS + 1);

* Last day for this iteration is the last day of the month five months from now ;
%let LAST_DAY = %sysfunc(intnx(month, &FIRST_DAY, 5, e));

* Do not go past the indicated last date to import ;
%if (&LAST_DAY > %sysevalf(&GLBL_LATEST_DATE_TO_IMPORT)) %then %do;
    %let LAST_DAY = %sysevalf(&GLBL_LATEST_DATE_TO_IMPORT);
%end;

* Show values this iteration ;

%put ITERATIONS = &ITERATIONS  FIRST_DAY = %sysfunc(putn(&FIRST_DAY, yymmddn8.))
     LAST_DAY = %sysfunc(putn(&LAST_DAY, yymmddn8.)) ;

* This is where the real work will happen ;
* For test purposes, create a simple dataset with the iteration number ;
data Work.table&ITERATIONS;
a = &ITERATIONS;
run;

* For the next iteration, the first day is the first day of the month six months from now ;
%let FIRST_DAY = %sysfunc(intnx(month, &FIRST_DAY, 6, b));

%end; * do while ;

* Checking ... ;
%put Did loop &ITERATIONS times.;

* Concatenate the work files which were produced ;
data work.concat;
set
%do i = 1 %to &ITERATIONS;
  work.table&i
%end;
; * end the set statement;
run;

* Show concatenated data set ;
proc print data=Work.concat noobs;
run;

%mend doit;

* Ok, go... ;
%doit;