SAS宏中%if%else和if else的区别

本文探讨了SAS宏中%if%else和普通if else语句的区别。若使用if else,变量会被解释为数值,如x&q可代表x1-x5。而if语句则将变量视为值,如id=1时,x1='张三'。若使用%if,变量被视为文本,例如x&q不会解析为变量x1的值,而是直接按文本处理。宏语句内仅处理宏变量,不涉及data步变量。

SAS宏中%if%else和if else的区别

data a;
	set x;
	%do m=1 %to 3;
		%do q=1 %to 5;
			if x&q^="nan" and &m=id and x&q="&&id&m&q"  then do;
				&&id&m&q=1;
				put '有值 且id相等' id= x&q= &&id&m&q=;
				end;

x数据集
上面代码是正常的if else语句,它可以把变量转变成数值,就是说x&q可以代表x1-x5,但是if语句是把变量解读成值,即id=1时x1=‘张三’,字符串张三。
if结果展示
可以了看到x&q^=“nan”,没有x变量等于nan的。说明if语句把变量解读成了值。
接下来看%if代码。

%do m=1 %to 3;
	%do q=1 %to 5;

		%if x&q=nan   %then %do;
			&&id&m&q=1;
			put '有值 且id相等' id= x&q= &&id&m&q=;
			%end;

这段语句执行没有打印任何内容。

data a;
	set x;
	%do m=1 %to 3;
		%do q=1 %to 5;
			%if x&q=x1   %then %do;
				&&id&m&q=1;
				put '有值 且id相等' id= x&q= &&id&m&q=;
				%end;

这段代码执行,有结果。说明%if语句将x&q解读成x1文本,并不会将x1的值解读出来。且宏if语句中不需要用“”区别字符串,宏if语句中所代表的内容,全部都是字面意义的字符串,没有data步变量存在。只能有宏变量。

%macro merge_csv_files; %let start_time = %sysfunc(time()); %put NOTE: 开始执行时间: %sysfunc(putn(&start_time, time12.3)); %local file_count i current_file all_vars file_counter; %let input_path = C:\Users\20536\Desktop\项目资料\zhiya\; %let output_file = C:\Users\20536\Desktop\项目资料\merged_data.csv; %if %sysfunc(fileexist("&input_path")) = 0 %then %do; %put ERROR: 输入路径不存在! &input_path; %return; %end; %put NOTE: 正在扫描CSV文件...; filename filelist "&input_path"; data file_list; length fname $ 200; handle = dopen("filelist"); if handle > 0 then do; count = dnum(handle); do i = 1 to count; fname = dread(handle, i); if prxmatch('/\.csv$/i', strip(fname)) then output; end; rc = dclose(handle); end; keep fname; run; filename filelist clear; proc sql noprint; select count(*) into :file_count trimmed from file_list; quit; %let file_count = %sysfunc(coalesce(&file_count, 0)); %put NOTE: 找到 &file_count 个CSV文件; %let file_counter = 0; %if &file_count > 0 %then %do; data merged; length _dummy 8; delete; run; %do i=1 %to &file_count; %let file_counter = %eval(&file_counter + 1); %put NOTE: 处理进度: &file_counter/&file_count (%.1f%%); %put NOTE: 正在处理文件 #&i; data _null_; set file_list (firstobs=&i obs=&i); call symputx('current_file', catx('\', "&input_path", fname), 'L'); run; %put NOTE: 文件路径: &current_file; %if %sysfunc(fileexist("&current_file")) = 0 %then %do; %put WARNING: 文件不存在,跳过: &current_file; %continue; %end; %let rc = 0; proc import datafile="&current_file" out=current_data dbms=csv replace; getnames=yes; guessingrows=500; run; %let rc = &syserr; %if &rc > 0 %then %do; %put ERROR: 导入文件失败: &current_file (RC=&rc); %continue; %end; proc append base=merged data=current_data force nowarn; run; proc delete data=current_data; run; %if %sysfunc(mod(&i, 10)) = 0 %then %do; %put NOTE: 释放内存...; proc datasets lib=work nolist nowarn; delete current_data; quit; %end; %end; %if %sysfunc(exist(merged)) and %sysfunc(attrn(merged, nobs)) > 0 %then %do; %put NOTE: 开始排序数据...; proc sort data=merged out=sorted; by '申请日'n; run; %put NOTE: 保存最终数据集...; data "&output_file"; set sorted; run; %put NOTE: 合并完成! 输出文件: &output_file; proc delete data=merged sorted; run; %end; %else %do; %put WARNING: 合并数据集为空!; %end; %end; %else %do; %put WARNING: 没有找到CSV文件!; %end; %let end_time = %sysfunc(time()); %let total_time = %sysfunc(putn(%sysevalf(&end_time - &start_time), time12.3)); %put NOTE: 执行完成! 总耗时: &total_time; %mend merge_csv_files; options mprint mlogic symbolgen fullstimer; %let test_mode = 1; %if %symexist(test_mode) and &test_mode = 1 %then %do; %put NOTE: 进入测试模式 (仅处理前5个文件); %macro merge_csv_files; %local file_count i current_file; %let input_path = C:\Users\20536\Desktop\项目资料\zhiya\; filename filelist "&input_path"; data file_list; length fname $ 200; handle = dopen("filelist"); if handle > 0 then do; count = dnum(handle); do i = 1 to min(count, 5); fname = dread(handle, i); if prxmatch('/\.csv$/i', strip(fname)) then output; end; rc = dclose(handle); end; keep fname; run; filename filelist clear; %include '/path/to/full_macro.sas'; %mend; %end; 以上代码显示” %IF 语句在开型代码中无效。”以及“ %END 语句在开型代码中无效“如何优化
最新发布
06-30
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值