I'm trying to make my SAS Teradata query a little more efficient.
I can get the where timestamp filter in the outer nest to work but it doesnt work when i try to place it in the inner nest. I know i'm overlooking something really simple. Thanks for the help!
SELECT *
FROM CONNECTION TO ODBC
(
SELECT name, ID, timestamp
FROM TD.table
WHERE
timestamp > 1764460800
)
/* where timestamp > 1764460800 */
/*outside nest*/
;
quit;
1764460800 = 11/30/2015
When using pass through, you need to 'pass through' valid syntax for the underlying database. In this case you are looking for:
proc sql;
SELECT *
FROM CONNECTION TO ODBC
(
SELECT name, ID, timestamp
FROM TD.table
WHERE
timestamp > date '2015-11-30' /* Teradata format */
)
where timestamp > 1764460800 /* SAS format */
;
quit;
Related
I created below SAS code to pull the data for particular a date.
%let date =2016-12-31;
proc sql;
connect to teradata as tera ( user=testuser password=testpass );
create table new as select * from connection tera (select acct,org
from dw.act
where date= &date.);
disconnect from tera;
quit;
There are situation where that particular date may be missing in the dataset due to holiday.
I thinking how to query the previous date(non-holiday) if the mention date in the %let statement is holiday
Before running your query you have to do a lookup or data check on the date you are using. You have two options:
Use a Date Dimension table in order identify/lookup holidays.
Count how many records you have for that date, if you get 0 obs for this date, use date+1 in your query.
I recommend using the date dimension table option.
Teradata has Sys_Calendar.Calendar view. You can use that in query, it has all the information regarding weekdays and others.
if you want to SAS way use weekday function and use call symput as shown below. Teradata needs single quote around the date, so it is better to have single quotes around when creating macro variable
data _null_;
/* this is for intial date*/
date_int = input('2016-12-31', yymmdd10.);
/* create a new date variable depending on weekday*/
if weekday(date_int) = 7 then date =date_int-2; /*sunday -2 days to get
friday*/
else if weekday(date_int) = 6 then date =date_int-1;/*saturday -1 day to get
friday*/
else date =date_int;
format date date_int yymmdd10.;
call symputx('date', ''''||put(date,yymmdd10.)||'''');
run;
%put modfied date is &date;
modified date is '2016-12-29'
Now you can use this macro variable in your pass through.
I have metrics sas table like below
work.met_table
Metrics_Id Metrics_desc
1 Count_Column
2 Sum_Column
3 Eliminate_column
I wanna do something like doing while loop in T-sql
select count(*) :cnt_tbl from work.met_table
%let init_cnt = 1
while (&init_cnt = &cnt_tbl)
begin
select Metrics_desc into :met_nm
from work.met_table
where metrics_id = 1
Insert into some_sas_table
Select * from another table where Metrics_desc =&met_nm
/* Here I wanna loop all values in metrics table one by one */
end
%put &init_cnt = &int_cnt+1;
How this can be done in proc sql? Thanks in advance
If you want to dynamically generate code then use the SAS macro language.
But for your example there is no need to dynamically generate code.
proc sql ;
insert into some_sas_table
select *
from another_table
where Metrics_desc in (select Metrics_desc from work.met_table)
;
quit;
You can also do an explicit pass through. Send your native t-sql code to run on the database Server through SAS rather than bringing the data to the SAS application server to query it.
The example below is explained in details here.
PROC SQL;
CONNECT TO ODBC(DATASRC=SQLdb USER=&SYSUSERID) ;
/* Explicit PASSTHRU with SELECT */
SELECT *
FROM CONNECTION TO ODBC (
SELECT b.idnum o.[SSdatecol] AS mydate
FROM dbo.big_SS_table1 b
LEFT JOIN dbo.other_SStable o
ON b.idnum = o.memberid
WHERE o.otherdatecol >= '2014-10-06'
--This is a T-SQL comment that works inside SQL Server
) ;
;
DISCONNECT FROM ODBC ;
QUIT;
I'm using a SAS access to oracle. and I want to see the query that SAS sends to Oracle.
assume that : oracle is the name of the oracle libname and local is the sas libname.
proc sql;
select *
from oracle.oracle_table ot
inner join local.sas_table st
on ot.customer_id = st.customer_id
;
quit;
I want to know if sas retrieves all data from the oracle table and then does the join or it's sending the list of the customer ids.
Thanks !
MK
Use sastrace to see how it's coming over from Oracle, and _method to see how they are being joined.
options sastrace=',,,d' sastraceloc=saslog;
proc sql _method;
select *
from oracle.oracle_table ot
inner join local.sas_table st
on ot.customer_id = st.customer_id
;
quit;
Just wondering how I can alter the following query to show date in the format I want. I am using SAS to pull this data.
Existing Date format: 15MAR2011:09:05:16.000000
Format I want: 15MAR2011:09:05:16
Query I am using:
proc sql;
create table data.test as
select * from connection to odbc
(
select ID,
DATE AS CREATION_DATE,
from maintable
);
quit;
A format affects how SAS displays a variable value. It does not affect the actual value itself.
So, assuming the variable CREATION_DATE is a datetime value, just assign it a format of DATETIME20. to display is as you want:
proc sql;
create table data.test as
select ID, CREATION_DATE format=datetime20.
from connection to odbc
( select ID, DATE AS CREATION_DATE
from maintable );
quit;
However, some ODBC interfaces will return your date column as a character string, so you need to be sure it is showing up on the SAS side as a proper datetime value.
I'm trying to automate a job that involves a lot of data being passed across the network and between the actual db2 server and our SAS server. What I'd like to do is take a traditional pass through...
proc sql;
connect to db2(...);
create table temp as
select * from connection to db2(
select
date
.......
where
date between &start. and &stop.
); disconnect from db2;
quit;
into something like this:
x "db2 'insert into temp select date ...... where date between &start. and &stop.'";
I'm running into a few issues the first of which is db2 date format of 'ddMONyyyy'd which causes the shell command to terminate early. If I can get around that I think it should work.
I can pass a macro variable through to the AIX (SAS) server without the extra set of ' ' needed to execute the db2 command.
Any thoughts?
You might get around the single-quote around the date issue by setting off the WHERE clause with a parenthesis. I'm not sure that this will work, but it might be worth trying.
As far as X command, try something like the following:
%let start = '01jan2011'd;
%let stop = '31dec2011'd;
%let command_text = db2 %nrbquote(')insert into temp select date ... where (date between &start. and &stop.)%nrbquote(');
%put command_text = &command_text;
x "&command_text";