Set variable in SELECT statement - sql-server-2008

I'm having the same problem as described here, unfortunately the solution does not work for MS SQL Server.
Does a similar syntax exist for MS SQL Server?
Note: my query is not as simple as in the example. I'd like to reuse DifferenceMinutes in the TooLateTime case.
DATEDIFF(MINUTE, DayOfWeekStopTime, GETDATE()) AS DifferenceMinutes,
CASE
WHEN DATEDIFF(MINUTE, DayOfWeekStopTime, GETDATE()) < 0 THEN NULL
ELSE CONVERT(varchar, GETDATE() - DayOfWeekStopTime, 108)
END AS TooLateTime

It's a little hard to tell exactly what you're trying to do, but I think this might be what you're looking for:
SELECT
DifferenceMinutes,
CASE
WHEN DifferenceMinutes < 0 THEN NULL
ELSE CONVERT(varchar, GETDATE() - DayOfWeekStopTime, 108)
END AS TooLateTime
FROM (
SELECT
DayOfWeekStopTime,
DATEDIFF(MINUTE, DayOfWeekStopTime, GETDATE()) AS DifferenceMinutes
FROM TableName
) X
You'll have to substitute your source table(s) for "TableName" in the FROM section of the inner query.
By rolling your calculated values into a nested select like this, you can refer to them by whatever name you give them in the outer query.
If you want to set variables for each of the values, you can do that as follows, but you'll need to make sure you're only returning one row from the query:
DECLARE #DifferenceMinutes int, #TooLateTime varchar(30)
SELECT
#DifferenceMinutes = DifferenceMinutes,
#TooLateTime = CASE
WHEN DifferenceMinutes < 0 THEN NULL
ELSE CONVERT(varchar, GETDATE() - DayOfWeekStopTime, 108)
END
FROM (
SELECT
DayOfWeekStopTime,
DATEDIFF(MINUTE, DayOfWeekStopTime, GETDATE()) AS DifferenceMinutes
FROM TableName
) X

Related

SQL select true if date comparison

Is it possible to return a boolean value as a select field if a date is less than a certain time?
For example, something like:
SELECT true IF (mydate < NOW())
or something like that?
SELECT
CAST(CASE WHEN mydate< getdate() THEN 1 ELSE 0 END AS bit) AS mydate
FROM
MyTable WHERE (ID = 1)
-- Another approach might be
SELECT
CAST(COUNT(*) AS bit) AS mydate
FROM
MyTable
WHERE
ID = 1 AND mydate < getdate()
You can simply inject an inline IF statement as below:
SELECT CAST(IIF(mydate < GETDATE(), 1, 0) AS BIT)

How to get hour and minute only from a DateTime

I have let's say
'2015-01-16 13:50:00.000'
in my database.
How do I get the hours and minute only ?
13:50
in the end I want to make query like this
Update A set status = 1 WHERE endTime = current_time()
*endTime = field name of my sample above.
SELECT DATEPART(HOUR, GETDATE());
SELECT DATEPART(MINUTE, GETDATE());
MSDN: DATEPART
I want to get 13:50. is it the way
SELECT CAST(DATEPART(HOUR, GETDATE())AS VARCHAR(2)) + ':' +
CAST(DATEPART(MINUTE, GETDATE())AS VARCHAR(2))
I'm on SQL-Server 2005 which has no TIME datatype, but this should also work for you:
SELECT LEFT(DATEADD(MINUTE, 10, (CONVERT(TIME(0),GETDATE()))),5)
If you want to filter your records by the hour+minute part:
WHERE DATEPART(HOUR, endTime)= DATEPART(HOUR, GETDATE())
AND DATEPART(MINUTE, endTime)= DATEPART(HOUR, GETDATE())
Try the following
SQL Server 2000/2005
SELECT
CONVERT(VARCHAR(8), GETDATE(), 108) AS HourMinuteSecond,
CONVERT(VARCHAR(10), GETDATE(), 101) AS DateOnly;
GO
SQL Server 2008 Onwards
SELECT
CONVERT(TIME, GETDATE()) AS HourMinuteSeconds;
SELECT
CONVERT(DATE, GETDATE()) AS DateOnly;
GO
you can learn about it more here

Need better current datetime syntax

This is current/old Access query I inherited.Need to retrieve the past year Case log. How can I write a better current date in Where clause?
Select (ID,DateLog,TimeLog)
From tblActiveCase
WHERE (((DatePart("yyyy",[DateLog])) Between DatePart("yyyy",Now())-1 And
DatePart("yyyy",Now())))
--My new StoredProc
Select (ID,DateLog,TimeLog)
From tblActiveCase
WHERE DateLog <= DATEADD(YEAR, -1, GETDATE())
is there a better way to write it?
declare #date date
set #date = DATEADD(YEAR, -1, GETDATE())
Select (ID,DateLog,TimeLog)
From tblActiveCase
WHERE DateLog >= #date

Select less and less records over time?

I'd like to write a query or stored procedure to retrieve less and less records over time from a relational database.
Think of this like populating the Google Finance stock chart: The past few days will have all ticks fit the day, and the further you go back, less and less ticks are displayed on each date. All ticks will show for today, 50% of ticks will show for one week ago, 30% for one month ago, and 10% for one year ago. Think of this like a gradient.
Is it possible to achieve this with one query? Or perhaps it would be necessary to use multiple queries? What might this look like?
Note that record ids are non-contiguous (there are gaps), but each record has a timestamp for determining order.
Also note that I am using MySQL.
Here is the structure of my table:
quotes
id
security_id
last_price
bid_price
ask_price
date
timestamp
trade_volume
cumulative_volume
average_volume
created_at
Sounds like you are looking for a constant set of records that represent the time-span. You can do so by defining a control date set.
Here's a sample query (doesn't account for weekends and holidays but that can be added):
POPULATE:
CREATE TABLE #quotes
(
id int identity(1,1)
,security_id VARCHAR(50)
,last_price FLOAT
,bid_price FLOAT
,ask_price FLOAT
,[date] DATETIME
,[timestamp] DATETIME
,trade_volume FLOAT
,cumulative_volume FLOAT
,average_volume FLOAT
,created_at DATETIME
)
DECLARE #i int
set #i = 100000
WHILE #i > 0
BEGIN
INSERT INTO #quotes (
security_id
,last_price
,bid_price
,ask_price
,[date]
,[timestamp]
,trade_volume
,cumulative_volume
,average_volume
,created_at
)
values( 'IBM US'
, 100.00 + RAND()
, 100.00 + RAND()
, 100.00 + RAND()
, DATEADD(MINUTE, -1* #i, GETDATE())
, DATEADD(MINUTE, -1* #i, GETDATE())
, 10000000.00 + RAND()*1000000.00
, 10000000.00 + RAND()*1000000.00
, 10000000.00 + RAND()*1000000.00
,getdate())
set #i= #i-1
END
You can change around the time span, but the following will give you around 1000 records that represent the set from start to finish.
DECLARE #StartDate DATETIME,
#EndDate DATETIME,
#j FLOAT,
#step FLOAT
set #StartDate = GETDATE()-20
SET #EndDAte = GETDATE()
set #j = 0.0
CREATE TABLE #TimeTable
(
IntervalDate DATETIME
)
--say you always want 1000 measures
--use the datediff value to define the step size:
select #step = DATEDIFF(MINUTE, #StartDate, #EndDate)/1000.0
WHILE #j < DATEDIFF(MINUTE, #StartDate, #EndDate)
BEGIN
INSERT #TimeTable (IntervalDate) VALUES (DATEADD(minute, #j, #StartDate))
SET #j = #j+#step
print #j
END
select security_id
,last_price
,bid_price
,ask_price
,[date]
,[timestamp]
,trade_volume
,cumulative_volume
,average_volume
,created_at
from #Quotes q
join #TimeTable t on dateadd(mi, datediff(mi, 0, q.date), 0) = dateadd(mi, datediff(mi, 0, t.IntervalDate), 0)

A simpler way to get the current time in SQL Server 2008

I need to store the current time (format 'hi') as char(4) in a table (is created and used by another program, I can't change it) and now wondered what is a suitable way to retrieve it via SQL. I know MySQL is not that standard-orientated, but I thought it could be something similiar to DATE_FORMAT(NOW(), 'Hi'). The code below which I found works, but feels little intricately.
SELECT CAST(DATEPART(hour, GETDATE()) AS nvarchar)+CAST(DATEPART(minute, GETDATE()) AS nvarchar);
Is there a better way to achieve this?
Following gives the same result:
SELECT LEFT(STUFF(CONVERT(NCHAR(8), GETDATE(), 8), 3, 1,''), 4)
It seems to have approximately the same performance as the method from question. I tested it like this:
DECLARE #i INT = 0,
#dto1 DATETIME2,
#dto2 DATETIME2
SET #dto1 = SYSDATETIME()
WHILE #i < 100000
BEGIN
PRINT LEFT(STUFF(CONVERT(NCHAR(8), GETDATE(), 8), 3, 1,''), 4)
SET #i = #i + 1
END
SET #dto2 = SYSDATETIME()
SELECT DATEDIFF(MILLISECOND, #dto1, #dto2)
Sql Server 2008 has a time datatype:
select replace(left(cast(getdate() as time), 5), ':', '')