我发现处理这些情况的最佳方法是使用自定义日期时间格式。您可以找到有关构建它们的链接here。我建议将格式保存到公共库中,以便您的 SAS 会话始终可以使用它。格式为:
proc format ;
picture mssqldt low-high = '''%Y-%0m-%0d %0H:%0M:%0S.000''' (datatype = datetime) ;
run ;
这将采用常规 SAS 日期时间戳并将其格式化(包括引号):
'2015-09-21 15:04:16.000'
将此合并到您的 SAS 代码中的最佳方法是始终将日期和日期时间保留在其 SAS 表示中,并为您的 SQL Server 格式化变量提供单独的变量。例如
计算我们想要使用的日期时间:
%let my_datetime = %sysfunc(datetime());
使用 SQL Server 格式的日期时间戳创建两个新变量。我总是打电话给我的&sql_start 和&sql_end,这样他们就可以很好地阅读,我永远不必考虑它......
%let sql_start = %sysfunc(sum(&my_datetime),mssqldt.);
%let sql_end = %sysfunc(intnx(minute,&my_datetime,1),mssqldt.);
您可以看到,为了计算sql_start,我使用了%sysfunc() 中的sum() 函数并传入了SAS 日期时间变量。我这样做是因为它不会更改日期时间的值,并且允许我使用 %sysfunc() 的第二个参数,它将指定的格式应用于返回的值。
对于sql_end,我照常使用intnx() 函数,并再次使用第二个%sysfunc() 参数对其进行格式化。
让我们打印出这些值来看看它们的样子:
%put &sql_start &sql_end;
给予:
'2015-09-21 15:04:16.000' '2015-09-21 15:05:00'
那么这只是在你的代码中使用它的一个例子:
proc sql;
...
where tmstmp between &sql_start and &sql_end;
quit;
所有代码都在一处(假设您已经定义了格式):
%let my_datetime = %sysfunc(datetime());
%let sql_start = %sysfunc(sum(&my_datetime),mssqldt.);
%let sql_end = %sysfunc(intnx(minute,&my_datetime,1),mysqldt.);
%put &sql_start &sql_end;
proc sql;
...
where tmstmp between &sql_start and &sql_end;
quit;
现在,如果您想一次提取一个数据,可以将其全部编译成这样的循环:
%macro get_data(iStart=,iEnd=);
%local tmp_start tmp_end sql_start sql_end;
%let tmp_start = &iStart;
%do %while(&tmp_start le &iEnd);
%let tmp_end = %sysfunc(intnx(hour,&tmp_start,0,end));
/* MAKE SURE END OF LOOP ISNT GREATER THAN END DATETIME */
%if &tmp_end > &iEnd %then %do;
%let tmp_end = &iEnd;
%end;
%let sql_start = %sysfunc(sum(&tmp_start),mssqldt.);
%let sql_end = %sysfunc(sum(&tmp_end ),mssqldt.);
/* DO SQL HERE */
%put &sql_start &sql_end;
/* INCREMENT THE LOOP */
%let tmp_start = %sysfunc(intnx(hour,&tmp_start,1,beginning));
%end;
%mend;
从今天到明天的某个时间调用它:
%get_data(iStart=%sysfunc(datetime()),
iEnd =%sysfunc(dhms(%sysfunc(date())+1,2,30,13))
);
结果运行时间如下:
'2015-09-21 15:25:33.000' '2015-09-21 15:59:59.000'
'2015-09-21 16:00:00.000' '2015-09-21 16:59:59.000'
'2015-09-21 17:00:00.000' '2015-09-21 17:59:59.000'
'2015-09-21 18:00:00.000' '2015-09-21 18:59:59.000'
'2015-09-21 19:00:00.000' '2015-09-21 19:59:59.000'
'2015-09-21 20:00:00.000' '2015-09-21 20:59:59.000'
'2015-09-21 21:00:00.000' '2015-09-21 21:59:59.000'
'2015-09-21 22:00:00.000' '2015-09-21 22:59:59.000'
'2015-09-21 23:00:00.000' '2015-09-21 23:59:59.000'
'2015-09-22 00:00:00.000' '2015-09-22 00:59:59.000'
'2015-09-22 01:00:00.000' '2015-09-22 01:59:59.000'
'2015-09-22 02:00:00.000' '2015-09-22 02:30:13.000'