I need someone to explain to me what is happening in the background in a compute block.
I am creating a report where I am comparing dates from 2 different reports. If there is a mismatching date, then I concatenate them. For example, you can see that the Baseline_Start_Date and Baseline_End_Date did not match between CDM and SM reports, so they are concatenated.
Baseline_Start_Date |
Baseline_End_Date |
Actual_Start_Date |
Actual_End_Date |
2023-06-30 (CDM) / 2020-10-20 (SM) |
2023-06-30 (CDM) / 2020-10-20 (SM) |
|
|
My task is to highlight Baseline_Start_Date when Actual_Start_Date is blank and Baseline_Start_Date is mismatching. I programatically determine if the dates are not matching if the length of the date field is greater than 20. Likewise, I need to highlight Baseline_End_Date when Actual_End_Date and Baseline_End_Date is mismatching. I'm trying to use a compute block, but I'm not sure how this works when using multiple variables in an IF statement. With the code below, it will highlight only when Baseline_Start_Date > 20 regardless of if Actual_Start_Date is blank or not. How do I incorporate the Actual_Start_Date condition as well?
compute Baseline_Start_Date;
if (missing(Actual_Start_Date)) & length(Baseline_Start_Date) > 20 then do;
call define('Baseline_Start_Date', "style", "style=[background=yellow]");
end;
endcomp;
When I specify a compute block, which variable should be placed there? I assumed Baseline_Start_Date because that is the variable that I want to conditionally highlight. But then inside the block, the condition is based on 2 variables (Baseline_Start_Date and Actual_Start_Date). Can someone explain to me how compute blocks work with multiple variables involved?
Hi:
My guess is that it has something to do with your COLUMN statement order of variables. The answer to this question will depend on the order in which the variables are defined in the COLUMN statement. This has been explained many times before in the Forum as the "left-to-right" rule of PROC REPORT. If you search you should find it.
In short, consider this COLUMN statement:
column sex age height weight;
If I want to do something based on age and height, maybe:
if age = 14 and height < 60 then do;
call define ( ...... );
end;
I cannot make this comparison in a COMPUTE block for AGE. That's because at the point in time when PROC REPORT is executing the COMPUTE block for AGE, it has ONLY placed SEX and AGE on the report row (working from LEFT to RIGHT). That means in the COMPUTE block for AGE, PROC REPORT does NOT have any visibility of the value for HEIGHT on that report row. PROC REPORT builds the report row one item at a time, working from left to right and at the point in time when a particular variable is placed on the report row, the COMPUTE block for that variable executes, so, if the comparison needs to be done between 2 items, both items will need to be placed on the report row for a successful comparison.
On the other hand, in the COMPUTE block for HEIGHT, when the COMPUTE block is being executed, PROC REPORT has placed SEX, AGE and HEIGHT on the report row, so both AGE and HEIGHT can be tested.
Search for some of the other postings on the left-to-right rule of PROC REPORT.
Cynthia
Some example data, just the variables needed for this bit and complete enough Proc Report code would be a good idea.
Hi:
My guess is that it has something to do with your COLUMN statement order of variables. The answer to this question will depend on the order in which the variables are defined in the COLUMN statement. This has been explained many times before in the Forum as the "left-to-right" rule of PROC REPORT. If you search you should find it.
In short, consider this COLUMN statement:
column sex age height weight;
If I want to do something based on age and height, maybe:
if age = 14 and height < 60 then do;
call define ( ...... );
end;
I cannot make this comparison in a COMPUTE block for AGE. That's because at the point in time when PROC REPORT is executing the COMPUTE block for AGE, it has ONLY placed SEX and AGE on the report row (working from LEFT to RIGHT). That means in the COMPUTE block for AGE, PROC REPORT does NOT have any visibility of the value for HEIGHT on that report row. PROC REPORT builds the report row one item at a time, working from left to right and at the point in time when a particular variable is placed on the report row, the COMPUTE block for that variable executes, so, if the comparison needs to be done between 2 items, both items will need to be placed on the report row for a successful comparison.
On the other hand, in the COMPUTE block for HEIGHT, when the COMPUTE block is being executed, PROC REPORT has placed SEX, AGE and HEIGHT on the report row, so both AGE and HEIGHT can be tested.
Search for some of the other postings on the left-to-right rule of PROC REPORT.
Cynthia
Cynthia,
You saved my day! Thank you! I had a concern like this not long ago, and I completely forgot about the left-to-right thing. This is starting to make sense to me. I am defining Baseline_Start_Date before Actual_Start_Date, so the solution was to simply assign the compute block to Actual_Start_Date instead of Baseline_Start_Date.
Thanks again!
Available on demand!
Missed SAS Innovate Las Vegas? Watch all the action for free! View the keynotes, general sessions and 22 breakouts on demand.
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.