split data and use it to select betweeen date - sql

first of all i have a data like this , lets say we call it columnA
ColumnA
XXX.202201.0001
XXS2.202103.0002
XXS1.202104.0003
the data have 3 part , for example XXX.202201.0001
XXX refer to a code of a place
202201 refer to a date with YYYYMM format
0001 just an a unique number
I have a task to get list of data with startDate and endDate filter. i just don't know know yet how to do it , to split and get that date number and filter it using start and end date.
i expect to get a list of data that filtered with startdate and enddate to columnA

Related

Start date and end date assigning based on date ranges and value change

I have two tables temp_N and temp_C . Table script and data is given below . I am using teradata
Table Script and data
First image is temp_N and second one is temp_C
Now I will try to explain my requirement. Key column for this two tables are 'nbr'. This two table contains all the changes for a particular period of time.( this is sample data and this two tables will get daily loaded based on the updates). Now I need to merge this two tables into one table with date range assigned correctly. The expected result is given below. To explain the logic behind the expected result, first row in the expected result, fstrtdate is the least date which from the two tables which is 2022-01-31 and for the same row if we notice the end date is given as 2022-07-10 as there is a change in the cpnrate on 2022-07-11. second row is start with 2022-07-11 giving the changed cpnrate, now when comes to third row there is a change in ntr on 2022-08-31 and the data is update accordingly. Please note all this are date fields, there wont be any timestamp, please ignore the timestamp in screenshots
Now I would like to know how to achieve this in sql or is it possible to achieve ?
You can combine all the changes into a single table and order by effective start date (fstrtdate). Then you can compute effective end date as day prior to next change, and where one of the data values is NULL use LAG IGNORE NULLS to "bring down" the desired previous not-NULL value:
SELECT nbr, fstrtdate,
PRIOR(LEAD(fstrtdate) OVER (PARTITION BY nbr ORDER BY fstrtdate)) as fenddate,
COALESCE(ntr,LAG(ntr) IGNORE NULLS OVER (PARTITION BY nbr ORDER BY fstrtdate)) as ntr,
COALESCE(cpnrate,LAG(cpnrate) IGNORE NULLS OVER (PARTITION BY nbr ORDER BY fstrtdate)) as cpnrate
FROM (
SELECT nbr, fstrtdate, max(ntr) as ntr, max(cpnrate) as cpnrate
FROM (
SELECT nbr, fstrtdate, ntr, NULL (DECIMAL(9,2)) as cpnrate
from temp_n
UNION ALL
SELECT nbr, fstrtdate, NULL (DECIMAL(9,2)) as ntr, cpnrate
from temp_c
) AS COMBINED
GROUP BY 1, 2
) AS UNIQUESTART
ORDER BY fstrtdate;
The innermost SELECTs make the structure the same for data from both tables with NULLs for the values that come from the other table, so we can do a UNION to form one COMBINED derived table with rows for both types of change events. Note that you should explicitly assign datatype for those added NULL columns to match the datatype for the corresponding column in the other table; I somewhat arbitrarily chose DECIMAL(9,2) above since I didn't know the real data types. They can't be INT as in the example, though, since that would truncate the decimal part. There's no reason to carry along the original fenddate; a new non-overlapping fenddate will be computed in the outer query.
The intermediate GROUP BY is only to combine what would otherwise be two rows in the special case where both ntr and cpnrate changed on the same day for the same nbr. That case is not present in the example data - the dates are already unique - but it might be necessary to do this when processing the full table. The syntax requires an aggregate function, but there should be at most two rows for a (nbr, fstrtdate) group; and when there are two rows, in each of the other columns one row has NULL and the other row does not. In that case either MIN or MAX will return the non-NULL value.
In the outer query, the COALESCEs will return the value for that column from the current row in the UNIQUED derived table if it's not NULL, otherwise LAG is used to obtain the value from a previous row.
The first two rows in the result won't match the screenshot above but they do accurately reflect the data provided - specifically, the example does not identify a cpnrate for any date prior to 2022-05-11.
nbr
fstrtdate
fenddate
ntr
cpnrate
233
2022-01-31
2022-05-10
311,000.00
NuLL
233
2022-05-11
2022-07-10
311,000.00
3.31
...
-
-
-
-

Calculate stdev over a variable range in SQL Server

Table format is as follows:
Date ID subID value
-----------------------------
7/1/1996 100 1 .0543
7/1/1996 100 2 .0023
7/1/1996 200 1 -.0410
8/1/1996 100 1 -.0230
8/1/1996 200 1 .0121
I'd like to apply STDEV to the value column where date falls within a specified range, grouping on the ID column.
Desired output would like something like this:
DateRange, ID, std_v
1 100 .0232
2 100 .0323
1 200 .0423
One idea I've had that works but is clunky, involves creating an additional column (which I've called 'partition') to identify a 'group' of values over which STDEV is taken (by using the OVER function and PARTITION BY applied to 'partition' and 'ID' variables).
Creating the partition variable involves a CASE statement prior where a given record is assigned a partition based on its date falling within a given range (ie,
...
, partition = CASE
WHEN date BETWEEN '7/1/1996' AND '10/1/1996' THEN 1
WHEN date BETWEEN '10/1/1996' AND '1/1/1997' THEN 2
...
Ideally, I'd be able to apply STDEV and the OVER function partitioning on the variable ID and variable date ranges (eg, say, trailing 3 months for a given reference date). Once this works for the 3 month period described above, I'd like to be able to make the date range variable, creating an additional '#dateRange' variable at the start of the program to be able to run this for 2, 3, 6, etc month ranges.
I ended up coming upon a solution to my question.
You can join the original table to a second table, consisting of a unique list of the dates in the first table, applying a BETWEEN clause to specify desired range.
Sample query below.
Initial table, with columns (#excessRets):
Date, ID, subID, value
Second table, a unique list of dates in the previous, with columns (#dates):
Date
select d.date, er.id, STDEV(er.value)
from #dates d
inner join #excessRet er
on er.date between DATEADD(m, -36, d.date) and d.date
group by d.date, er.id
order by er.id, d.date
To achieve the desired next step referenced above (making range variable), simply create a variable at the outset and replace "36" with the variable.

How to generate columns in sql server?

I have following table in sql server.
ID ,EventID ,EventDate ,Title ,Type
Now I want to make query in below logic.
if user enter fromdate and todate. Here event are weekly or biweekly.
so let say fromdate '03/01/2016' to '03/31/2016 and type biweekly. Means columns are every biweekly.
so I want to generate query like.
3/1/2016 to 3/15/2016 | 3/16/2016 to 3/30/2016-these 2 biweekly are columns
if I pass so let say fromdate '03/01/2016' to '03/31/2016 and type weekly.
then columns should like every week
3/1/2016 to 3/8/2016 | 3/9/2016 to 3/16/2016 |3/17/2016 to 3/24/2016 and so on to till end date(To).
and rows of above output is Title.
How can this possible in sql server?
Get biweekly/weekly value. Let's say the user selects weekly. The value would be 7.
Use a loop to generate the columns. For instance, column1 would be the StartDate_to_EndDate. The StartDate would be the value the user entered. The EndDate would be the StartDate + 7 days(The value from #1 above)
Loop Through to get the second column etc etc (until the EndDate the user specified)

divide two table value in SSRS

I´ve got two tables in my Report:
I would like to divide the value from Scrap with the value from Table Total
--> (16227 / 425841) * 100
This is the code:
Select date as Datetime, tevent.name as Event, SUM(value) as sum
from tCount inner join tEvent ON tCount.eventid = tevent.id
where Name in ('Drive Fast', 'Drive Slow')
and date > getdate() -1
and tevent.Name in ('E01','E02','E03','E04','E05','E06','E07','E08')
and CalName = 'Drive'
The sum of these: 'E01','E02','E03','E04','E05','E06','E07','E08', I did it in the report like this: Sum(Fields!E01.Value+Fields!E02.Value+Fields!E03.Value+...
And for the other table it looks like this:
Select date as Datetime, tevent.name as Event, SUM(value) as sum
from tCount inner join tEvent ON tCount.eventid = tevent.id
where Name in ('Drive Normal')
and date > getdate() -1
and tevent.Name in ('E01','E02','E03','E04','E05','E06','E07','E08')
and CalName = 'Drive'
And I must do a division of this two statements.
But if I put in the Scrap Expression the value from Total then the result is wrong. Hope you can help me.
From what I understand of your question, you have two datasets, and you want to calculate the percentage of Scrap of the Total
To replicate your problem I have created two DataSets as follows
Scrap Dataset
myDateTime Event mySum
01/01/2015 Scrap 16227
02/01/2015 Scrap 14637
03/01/2015 Scrap 14174
Total Dataset
myDateTime Event mySum
01/01/2015 Total 425841
02/01/2015 Total 434024
03/01/2015 Total 405216
Create a Table in your report and set column 1 to be mySum from ScrapDataSet
Then you can use the LOOKUP function in Column 2 to look up a specific value from another dataset assuming there is a common field. In this instance
=Lookup(Fields!myDateTime.Value,
Fields!myDateTime.Value,
Fields!mySum.Value,
"TotalDataSet")
Compares myDateTime in ScrapDataSet to myDateTime in TotalDataSet, and where there is a match returns mySum from TotalDataSet
You can then combine these two expressions as follows to get the percentage as required in Column 3
=Fields!mySum.Value /
(Lookup(Fields!myDateTime.Value,
Fields!myDateTime.Value,
Fields!mySum.Value,
"TotalDataSet"))
In this example I formatted this third column to be a percentage format to 2 decimal places.
These steps result in a table that looks like this
Hopefully this is the output you require. If you need further assistance please ask with clarification of the original question.
As a final note Sum and DateTime are not recommended field names as these are both keywords that can be used in SSRS to either define a type of perform a function. These should really be renamed – as I have done in the example above.

Visual Foxpro - Specific date subtracting two columns of numeric date and compare result

I am new to visual foxpro. I am trying to write the sql statements.
There are two columns of dates, data type is in numeric.
Column A date is in the YYYYMMDD format.
Column B date is in the YYYYMM format. DD is not available, thus I am only comparing the YYYYMM.
I need to subtract or find the difference between a specific date e.g. 31 August 2015 and the dates in column A and B. Once I have the difference, I need to compare and see if the difference in Column B is greater than Column A.
What I have thought is using substr and split the dates to YYYY and MM. Then I subtract it from the specific date, and then compare the YYYY portion to see if it column B is greater than column A.
Your description sounds as if columnA / 100 would give a comparable format.
So if you've got test data like these
CREATE CURSOR test (columnA Num(8), columnB Num(6))
INSERT INTO test VALUES (20150802, 201508)
INSERT INTO test VALUES (20150712, 201506)
... you can get all rows where colmumnB equals converted(columnA):
SELECT * FROM test WHERE INT(columnA / 100) = columnB
... or get the difference between A and B for all rows:
SELECT INT(columnA/100) - columnB FROM test
Or if you've got a date-type parameter, you can for example get all rows where columnB would match the parameter:
d = DATE(2015,8,31)
SELECT * FROM test WHERE columnB = YEAR(d) * 100 + MONTH(d)
If you want to do something different, I'd suggest to edit the question and add more details