I have this codeblock for xst-fo
<codeblock outputclass="language-c"><![CDATA[
#define VALUE1 100 /* Comment */
#define VALUE2 200 /* Comment */
#define VALUE3 300 /* Comment */
#define VALUE4 400 /* Comment */]]></codeblock>
But when the pdf is generated I get this output:
Only the first comment in the #define list is good. The rest is not highlighted.
What is wrong with this?
Related
I'm trying to do simple calculations but I'm new and SAS is not intuitive to me.
Suppose I have this table.
data money;
infile datalines delimiter=",";
input name $ return $ invested;
datalines;
Joe,10,100
Bob,7,50
Mary,80,1000
;
Which creates this
/* name | return | invested */
/* _________________________ */
/* Joe | 10 | 100 */
/* Bob | 7 | 50 */
/* Mary | 80 | 50 */
I have three things I would like to do for my job that just switched over to SAS.
I need to make sure columns return and invested are numeric. When I run the code above, return column ends up being a CHAR column and I don't know why.
Now I want to create a new column and calculate the share of the total return they each got. In this case, the sum of return=97. This is the result I want.
/* name | return | invested | share_of_return */
/* ____________________________________________ */
/* Joe | 10 | 100 | 10.30% */
/* Bob | 7 | 50 | 7.22% */
/* Mary | 80 | 50 | 82.47% */
Next I want to find their ROI. Which is (return-investment) / investment * 100. This is the result I am looking for
/* Find ROI */
/* name | return | invested | share_of_return | ROI */
/* ___________________________________________________ */
/* Joe | 10 | 100 | 10.30% | -90% */
/* Bob | 7 | 50 | 7.22% | -86% */
/* Mary | 80 | 50 | 82.47% | 60% */
I appreciate your explanations and guidance in advanced. This is for a work project and we just switched over to SAS
1 & 3 are easy, 2 is slightly more difficult.
Remove $ in INPUT statement. $ indicates character. In your data you may need to convert it using the input function instead though.
Fix for example:
input name $ return invested;
Fix for actual data using input function. Note that you cannot convert types in a data step to the same name so I rename it while reading it in using the rename data set option.
data money2;
set money (rename = return = return_char);
return = input(return_char, best.);
drop return_char;
run;
Add total value to data step, SQL is fastest here:
proc sql;
create table money3 as
select *, sum(return) as return_total, return/calculated return_total as return_percentage f=percent12.1
from money2;
quit;
I outline two different methods of doing this here
Within a data step, add your calculation. It's probably most efficient if it can be done in first step.
Since a data step loops automatically you write the formula pretty much as shown. In this case I've also applied a format so it shows as a percentage but that requires you to not multiply it by 100. Depending on what you're doing next it may be best to leave it as numeric.
data money2;
set money (rename = return = return_char);
return = input(return_char, best.);
ROI = (return - investment)/investment;
format ROI percent12.1;
run;
drop return_char;
run;
i have some problem with doxygen documentation.
I want to have something like
E_SOME_ERROR | 0x000001 Detailed info about this error
Important think is that I need values generated by doxygen but I can't find any solution. Do you guys know if this is possible?
So for example
/**
* #brief Enum with error codes.
*/
enum enumName
{
ONE, /**< {HEX value} - 1st number */
TWO, /**< {HEX value} - 2nd number */
THREE, /**< {HEX value} - 3rd number */
FOUR, /**< {HEX value} - 4th number */
}
Should be generated in pdf like:
--------------------------------
| ONE | 0x0001 - 1st number |
--------------------------------
| TWO | 0x0002 - 2nd number |
--------------------------------
| THREE | 0x0003 - 3rd number |
--------------------------------
| FOUR | 0x0004 - 4th number |
--------------------------------
And each {HEX value} have to be generated by some macro or something like this not hardcoded.
I need to form a line concatenating numbers and strings, but separated by a space.
I tried it in 5 ways, but it didn't give the desired result.
%LET lim1 = 113;
%LET lim2 = 166;
Test 1:
%LET linha = %SYSFUNC(CATS(De,&lim1,a,&lim2,clientes));
%PUT &linha;
Out 1:
De113a166clientes
Test 2:
%LET linha = %SYSFUNC(CATS('De ',&lim1,' a ',&lim2,' clientes'));
%PUT &linha;
Out 2 (Error):
30 %LET linha = %SYSFUNC(CATS('De ',&lim1,' a ',&lim2,' clientes'));
NOTE: Line generated by the macro function "SYSFUNC".
30 'De '113' a '166' clientes'
_____ _____
49 49
NOTE 49-169: The meaning of an identifier after a quoted string might change in a future SAS release. Inserting white space
between a quoted string and the succeeding identifier is recommended.
Test 3:
%LET linha = %SYSFUNC(CATX(' ','De ',&lim1,' a ',&lim2,' clientes'));
%PUT &linha;
Out 3 (Error):
29 %LET linha = %SYSFUNC(CATX(' ','De ',&lim1,' a ',&lim2,' clientes'));
NOTE: Line generated by the macro function "SYSFUNC".
29 'De '' '113' '' a '' '166' '' clientes'
________ ___________
49 49
NOTE 49-169: The meaning of an identifier after a quoted string might change in a future SAS release. Inserting white space
between a quoted string and the succeeding identifier is recommended.
Test 4:
%LET linha = %SYSFUNC(CATX(' ',De,&lim1,a,&lim2,clientes));
%PUT &linha;
Out 4 (Error):
NOTE: Line generated by the macro function "SYSFUNC".
29 De' '113' 'a' '166' 'clientes
___ ___ ___ ___
49 49 49 49
NOTE 49-169: The meaning of an identifier after a quoted string might change in a future SAS release. Inserting white space
between a quoted string and the succeeding identifier is recommended.
Test 5:
%LET linha = %SYSFUNC(CATX(*,De,&lim1,a,&lim2,clientes));
%PUT &linha;
Out 5:
De*113*a*166*clientes
Test 5 is as close as I need, but I need to replace * with a blank space.
I need: De 113 a 166 clientes
Unfortunately, I was not successful.
In macro you don't need to use CAT for assembling a source code text.
Just resolve the macro variables in the context desired.
%LET lim1 = 113;
%LET lim2 = 166;
%LET linha = De &lim1 a &lim2 clientes;
%PUT &=linha;
----- LOG -----
LINHA=De 113 a 166 clientes
If using a macro variable value in the DATA step context of a quoted string or string value computation the resolution should be within double quotes of a string literal (unless the macro value is already literally double quoted text)
data have;
input (part1-part3) ($);
datalines;
De a clientes
Si o consumer
Mr A Sky
;
%LET lim1 = 113;
%LET lim2 = 166;
data want;
set have;
result = catx(' ', part1, "&lim1", part2, "&lim2", part3);
put result=;
run;
----- LOG -----
result=De 113 a 166 clientes
result=Si 113 o 166 consumer
result=Mr 113 A 166 Sky
I was wondering if there was a way to quickly create a box around a comment in SAS. Currently you can use a command Ctrl + Shift + / to create comments such as this
/*This is a comment*/
/*This is the second line of the comment*/
I would like to know if anyone has a solution to box in multiple lines of comments, like this:
/******************************************/
/* This is a comment */
/* This is the second line of the comment */
/******************************************/
Currently the only way I know how to create boxes like this is to manually type in asterisks and add spaces until the code lines up. I'm hoping there is a more efficient solution.
This macro will create the comment box in the log. You can then copy and paste it into your code.
It uses '/' as the default delimiter to split the lines. But this can be changed when calling the macro, as shown below.
%macro comment_box(comment, delimiter='/');
/* count the number of line using the delimiter */
%let line_count = %sysevalf(%sysfunc(countc(%str(&comment.), &delimiter.)) + 1);
%let max_line_len = 0;
/* loop through to split the text into lines measure the line length including leading&trailing blanks */
%do x=1 %to &line_count.;
%let line&x. = %scan(%str(&comment.), &x., &delimiter.);
%let line&x._len = %sysevalf(%length(%str(&&line&x..)) + 2);
%if &&line&x._len. > &max_line_len. %then %let max_line_len = &&line&x._len.;
%end;
/* Create the top/bottom box line matching to the max text line length */
/* Add the comment box to the log using PUT statements. */
option nonotes;
data _null_;
line_count = &line_count.;
max_line_len = &max_line_len.;
box_line = cat('/*', repeat('*', max_line_len - 1), '*/');
%do x=1 %to &line_count.;
%if &max_line_len. = &&line&x._len. %then %do;
line&x. = cat('/* ', "&&line&x..", ' */');
%end;
%else %do;
line&x. = cat('/* ', "&&line&x..", repeat(' ', %sysevalf(&max_line_len. - &&line&x._len. - 1)), ' */');
%end;
%end;
/* add the comment box to the log */
put box_line;
%do x=1 %to &line_count.;
put line&x.;
%end;
put box_line;
run;
option notes;
%mEnd;
%comment_box(%str(This is a comment/This is the second line of the comment));
%comment_box(%str(This is a comment+This is the second line of the comment), delimiter= '+');
Assuming you're using enterprise guide, have you tried using the keyboard macro section?
Example
This is a very quick one that just inserts a /*****/ of a set length but there might be enough functionality in there to correctly set the length of this by the length of your comment.
You can then assign it to a key combination.
I am working on a report in Base SAS 8.1(OpenVMS). I need it to have 1 page per observation...similar to below. I can't find anything that shows how to do this with PROC PRINT or PROC REPORT. Is there any way to do this other than with the PUT statement? Upgrading or adding modules isn't an option unfortunately. Any help is appreciated.
Header Text Observation ID 1
Line 1 text ---------------- variable 1
Line 2 text ---------------- variable 2
Line 3 text ---------------- variable 3
--page break --
Header Text Observation ID 2
Line 1 text ---------------- variable 1
Line 2 text ---------------- variable 2
Line 3 text ---------------- variable 3
--page break --
If you transpose the dataset by the observation number, then proc report can handle it with no problem. hth.
/* test data -- each obs is identified by obsId */
data class;
set sashelp.class;
obsId = _n_;
run;
/* transpose the data */
proc transpose
data=class
out=report(rename=(_name_=var col1=value));
var _all_;
by obsId;
run;
/* change the varaible name into "Line 1 text ..." */
data report;
drop line cLine dashes;
length var cLine $30;
dashes = repeat("-", 20-1);
/* usual DoW */
do line = 1 by 1 until (last.obsId);
set report;
by obsId;
cLine = put(line, best.-l);
var = "Line "||trim(cline)||" text "||dashes;
output;
end;
run;
/* print out one obs per page */
options nocenter;
proc report data=report nowd;
column obsId var value;
define obsId / " " group noprint;
define var / " " display left;
define value / " " display left;
break after obsId / page;
compute before obsId;
id = put(obsId, best.-l);
len = length(id);
line #2 "Header Text Observation Id " iD $varying. len;
line " ";
endcomp;
run;
/* on lst, in part.
Header Text Observation Id 1
Line 1 text ------------------ Alfred
Line 2 text ------------------ M
Line 3 text ------------------ 14
Line 4 text ------------------ 69
Line 5 text ------------------ 112.5
Line 6 text ------------------ 1
(new page)
Header Text Observation Id 2
Line 1 text ------------------ Alice
Line 2 text ------------------ F
Line 3 text ------------------ 13
Line 4 text ------------------ 56.5
Line 5 text ------------------ 84
Line 6 text ------------------ 2
(new page)
...
*/