alt text http://img187.imageshack.us/img187/8453/testhc3.png
alt text http://img145.imageshack.us/img145/3306/test2bn4.png
The first picture is my query. I need to obtain results in second picture.
select OrarioA, OrarioB, MAX(VW_DettaglioOrariLinee_FromAToB.IDOrario), dbo.VW_DettaglioOrariLinee_FromAToB.IDDettaglioOrarioA, dbo.VW_DettaglioOrariLinee_FromAToB.IDDettaglioOrarioB
FROM dbo.VW_DettaglioOrariLinee_FromAToB INNER JOIN
Tb_Linee ON dbo.VW_DettaglioOrariLinee_FromAToB.IDRelA = Tb_Linee.IDRelA AND
dbo.VW_DettaglioOrariLinee_FromAToB.IDRelB = Tb_Linee.IDRelB INNER JOIN
dbo.periodi ON dbo.VW_DettaglioOrariLinee_FromAToB.IDOrario = dbo.periodi.IDOrario INNER JOIN
dbo.relgiornisettimanaorarilinee ON dbo.VW_DettaglioOrariLinee_FromAToB.IDOrario = dbo.relgiornisettimanaorarilinee.IDOrario
This is my real query:
WITH Tb_Linee AS
(
SELECT * FROM VW_rellineestazionamenti
WHERE
IDLINEA = #IDLINEA
AND
IDStazA = #IDStazA
AND
IDStazB = #IDStazB
AND
PosizioneA = #PosizioneA
AND
PosizioneB = #PosizioneB
)
select OrarioA, OrarioB, VW_DettaglioOrariLinee_FromAToB.IDOrario, dbo.VW_DettaglioOrariLinee_FromAToB.IDDettaglioOrarioA, dbo.VW_DettaglioOrariLinee_FromAToB.IDDettaglioOrarioB
FROM dbo.VW_DettaglioOrariLinee_FromAToB INNER JOIN
Tb_Linee ON dbo.VW_DettaglioOrariLinee_FromAToB.IDRelA = Tb_Linee.IDRelA AND
dbo.VW_DettaglioOrariLinee_FromAToB.IDRelB = Tb_Linee.IDRelB INNER JOIN
dbo.periodi ON dbo.VW_DettaglioOrariLinee_FromAToB.IDOrario = dbo.periodi.IDOrario INNER JOIN
dbo.relgiornisettimanaorarilinee ON dbo.VW_DettaglioOrariLinee_FromAToB.IDOrario = dbo.relgiornisettimanaorarilinee.IDOrario
If you want to partition by OrarioA only:
SELECT OrarioA, OrarioB, IDOrario, IDDettaglioOrarioA, IDDettaglioOrarioB
FROM (
SELECT *, ROW_NUMBER() OVER (PARTITION BY OrarioA ORDER BY OrarioB DESC, IDOrario DESC) AS rn
FROM table
) t
WHERE rn = 1
, this will result in the resultset as on picture 2.
If you want to partition by OrarioA and OrarioB:
SELECT OrarioA, OrarioB, IDOrario, IDDettaglioOrarioA, IDDettaglioOrarioB
FROM (
SELECT *, ROW_NUMBER() OVER (PARTITION BY OrarioA, OrarioB ORDER BY IDOrario DESC) AS rn
FROM table
) t
WHERE rn = 1
, but this won't filter out the first row in your resultset.
From the data you explained in your screenshots, I understand it as you need the id fields for the most highest IDOrario grouped by OrarioA and OrarioB?
SELECT IDDettaglioOrarioA, IDDettaglioOrarioB
FROM TABLE
GROUP BY
OrarioA, OrarioB
ORDER BY IDOrario DESC
If you need to select more columns, select any more at will.
Related
By running the following query I realized that I have duplicates on the column QueryExecutionId.
SELECT DISTINCT qe.QueryExecutionid AS QueryExecutionId,
wfi.workflowdefinitionid AS FlowId,
qe.publishing_date AS [Date],
c.typename AS [Type],
c.name As Name
INTO #Send
FROM
[QueryExecutions] qe
JOIN [Campaign] c ON qe.target_campaign_id = c.campaignid
LEFT JOIN [WorkflowInstanceCampaignActivities] wfica ON wfica.queryexecutionresultid = qe.executionresultid
LEFT JOIN [WorkflowInstances] wfi ON wfica.workflowinstanceid = wfi.workflowinstanceid
WHERE qe.[customer_idhash] IS NOT NULL;
E.g. When I test with one of these QueryExecutionIds, I can two results
select * from ##Send
where QueryExecutionId = 169237
We realized the reason is that these two rows have a different FlowId (second returned value in the first query). After discussing this issue, we decided to take the record with a FlowId that has the latest date. This date is a column called lastexecutiontime that sits in the third joined table [WorkflowInstances] which is also the table where FlowId comes from.
How do I only get unique values of QueryExecutionId with the latest value of WorkflowInstances.lastexecution time and remove the duplicates?
You can use a derived table with first_value partitioned by workflowinstanceid ordered by lastexecutiontime desc:
SELECT DISTINCT qe.QueryExecutionid AS QueryExecutionId,
wfi.FlowId,
qe.publishing_date AS [Date],
c.typename AS [Type],
c.name As Name
INTO #Send
FROM
[QueryExecutions] qe
JOIN [Campaign] c ON qe.target_campaign_id = c.campaignid
LEFT JOIN [WorkflowInstanceCampaignActivities] wfica ON wfica.queryexecutionresultid = qe.executionresultid
LEFT JOIN
(
SELECT DISTINCT workflowinstanceid, FIRST_VALUE(workflowdefinitionid) OVER(PARTITION BY workflowinstanceid ORDER BY lastexecutiontime DESC) As FlowId
FROM [WorkflowInstances]
) wfi ON wfica.workflowinstanceid = wfi.workflowinstanceid
WHERE qe.[customer_idhash] IS NOT NULL;
Please note that your distinct query is pertaining to the selected variables,
eg. Data 1 (QueryExecutionId = 169237 and typename = test 1)
Data 2 (QueryExecutionId = 169237 and typename = test 2)
The above 2 data are considered as distinct
Try partition by and selection the [seq] = 1 (the below code are partition by their date)
SELECT *
into #Send
FROM
(
SELECT *,ROW_NUMBER() OVER (PARTITION BY [QueryExecutionid] ORDER BY [Date] DESC) [Seq]
FROM
(
SELECT qe.QueryExecutionid AS QueryExecutionId,
wfi.FlowId,
qe.publishing_date AS [Date], --should not have any null values
qe.[customer_idhash]
c.typename AS [Type],
c.name As Name
FROM [QueryExecutions] qe
JOIN [Campaign] c
ON qe.target_campaign_id = c.campaignid
LEFT JOIN [WorkflowInstanceCampaignActivities] wfica
ON wfica.queryexecutionresultid = qe.executionresultid
LEFT JOIN
(
SELECT DISTINCT workflowinstanceid, FIRST_VALUE(workflowdefinitionid) OVER(PARTITION BY workflowinstanceid ORDER BY lastexecutiontime DESC) As FlowId
FROM [WorkflowInstances]
) wfi ON wfica.workflowinstanceid = wfi.workflowinstanceid
) a
WHERE [customer_idhash] IS NOT NULL
) b
WHERE [Seq] = 1
ORDER BY [QueryExecutionid]
I am trying to select the max image entry in a table based on the year and then the sequence number so that I can update a 2nd table with the correct image file name. In the example below sequence #, 2005765, is the correct image file.
I have attempted to do this with:
WITH CTE (Year, ImageId, ImageSeq) AS
(
SELECT
MAX(Year),
Image_ID,
Image_Seq
FROM
PIMAGE
WHERE
Type = 'PHOTO'
GROUP BY
Image_ID, Image_Seq
)
SELECT
cp.RPID,
MAX(i.Sequence),
i.File_Name
FROM
CommProperty cp
LEFT OUTER JOIN
CTE ON CTE.ImageId = cp.RPID
INNER JOIN
PIMAGE i ON i.Image_ID = cte.ImageId
AND i.Year = cte.Year
AND i.Image_Seq = cte.ImageSeq
WHERE
cp.RPID = 16107
GROUP BY
cp.RPID, i.File_Name
The simplest way is to use row_number():
SELECT p.*
FROM (SELECT p.*,
ROW_NUMBER() OVER (PARTITION BY image_id ORDER BY year DESC, image_seq DESC) as seqnum
FROM PIMAGE p
WHERE p.Type = 'PHOTO'
) p
WHERE seqnum = 1;
I have created a table in html to display first rows of each id and allow user to select specific range they want to see, but not sure how I can write it in query.
With results as
(
i.*,
ROW_NUMBER() OVER (PARTITION BY i.ID ORDER BY I.ID DESC) AS [RN]
FROM HolidayList AS I
INNER JOIN (
SELECT ID, MIN(CreateDate) FROM HolidayList GROUP BY ID
)
AS j ON i.ID = j.ID AND i.CreateDate = j.CreateDate
)
SELECT * FROM results WHERE [RN] = 1;
UPDATED
I have tried to inject two ROW_NUMBER(), but what I received is row 10 and row 25 and they are first rows of some specific id.
With results as
(
i.*,
ROW_NUMBER() OVER (PARTITION BY i.ID ORDER BY I.ID DESC) AS [RN],
ROW_NUMBER() OVER (ORDER BY I.ID) AS [R]
FROM HolidayList AS I
INNER JOIN (
SELECT ID, MIN(CreateDate) FROM HolidayList GROUP BY ID
)
AS j ON i.ID = j.ID AND i.CreateDate = j.CreateDate
)
SELECT * FROM results WHERE [RN] = 1 AND BETWEEN [R]>10 AND [R]<25
What I am really looking for is select a specific range from all the first row for each id.
FINAL
Thank to McGlothlin, finally I solve it. What I need is a nested CTE.
With First_CTE as
(
i.*,
ROW_NUMBER() OVER (PARTITION BY i.ID ORDER BY I.ID DESC) AS [RN]
FROM HolidayList AS I
INNER JOIN (
SELECT ID, MIN(CreateDate) FROM HolidayList GROUP BY ID
)
AS j ON i.ID = j.ID AND i.CreateDate = j.CreateDate
),
results AS
(
SELECT k.*,
ROW_NUMBER() OVER (ORDER BY k.ID DESC) AS [R]
FROM First_CTE AS k WHERE k.[RN] = 1
)
SELECT * FROM results WHERE [R]>10 AND [R]<25
The problem lies in this line:
ROW_NUMBER() OVER I.ID AS [R]
I think what you meant was:
ROW_NUMBER() OVER (ORDER BY I.ID) AS [R]
This is assuming you want to give it a row count over every row that is returned in the CTE. The ROW_NUMBER() function requires an ORDER BY to be specified, and the OVER clause would still require parentheses if you were using a function like SUM that could be used without an ORDER BY.
Edit: Based on your comment, it sounds like what you're looking for is an OFFSET. In that case you would remove the second ROW_NUMBER and include something like this:
ORDER BY ID OFFSET 10 ROWS FETCH FIRST 15 ROWS ONLY
This returns rows 11 to 25, sorted by ID.
Since the OFFSET syntax doesn't work in SQL Server 2008, you should do something like this as your end result:
With results as
(
i.*,
ROW_NUMBER() OVER (PARTITION BY i.ID ORDER BY I.ID DESC) AS [RN]
ROW_NUMBER() OVER (ORDER BY I.ID) AS [R]
FROM HolidayList AS I
INNER JOIN (
SELECT ID, MIN(CreateDate) FROM HolidayList GROUP BY ID
)
AS j ON i.ID = j.ID AND i.CreateDate = j.CreateDate
)
SELECT *
FROM results
WHERE [RN] = 1
AND [R] BETWEEN 11 AND 25
I have the following table structure:
id|date|studenttypeid|name|audituser
1|.....|4|Jason|....
2|.....|4|Robin|....
3|.....|4|Jason|....
4|.....|4|Dan|....
5|.....|4|Robin|....
I need to list all records which are duplicates on studenttypeid + name.
With the above data, the query should give me the following output:
1|.....|4|Jason|....
2|.....|4|Robin|....
3|.....|4|Jason|....
5|.....|4|Robin|....
How can I achieve this on SQL Server 2008?
You can use a group by and then join back to the original table, like this:
WITH Temp(StudentTypeId, Name) AS(
SELECT
StudentTypeId, Name
FROM YourTable
GROUP BY
StudentTypeId, Name
HAVING Count(1) > 1
)
SELECT YourTable.*
FROM YourTable
INNER JOIN Temp
ON YourTable.StudentTypeId = Temp.StudentTypeId
AND YourTable.Name = Temp.Name
you can use ROW_NUMBER()
SELECT ID, DATE, studenttypeid, name, audituser
FROM
(
SELECT ID, DATE, studenttypeid, name, audituser,
ROW_NUMBER() OVER (PARTITION BY studenttypeid, name
ORDER BY id) rn
FROM yourTableName
) a
WHERE rn = 1
SQLFiddle Demo
If you want to include every occurrence of the duplicates, some more methods using CROSS APPLY...
SELECT p.*
FROM people p
CROSS APPLY (
SELECT TOP(1) * FROM people p2 WHERE p2.ID <> p.ID AND p2.name = p.name AND p.studenttypeid = p2.studenttypeid
) as pWithDups
Or an EXISTS check
SELECT p.*
FROM people p
WHERE EXISTS (
SELECT *
FROM people p2
WHERE p2.ID <> p.ID AND p2.name = p.name AND p.studenttypeid = p2.studenttypeid
)
Try this
SELECT a.*
FROM yourtable a
JOIN (SELECT studenttypeid,
name
FROM yourtable
GROUP BY studenttypeid,
name
HAVING Count(studenttypeid) > 1) b ON b.name = a.name
ORDER BY a.id
i have a table similar this
id-value-RowInid
1-xy-1
1-xx-2
1-xz-3
2-xx-1
2-xr-2
3-xq-1
4-xa-1
4-xc-2
...
i need a function for this table with similar output to get maximum of RowInid in separated id group
1-xz-3
2-xr-2
3-xq-1
4-xc-2
...
You just need to use MAX(RowInid) with GROUP BY Id, value
SELECT ID, VALUE, MAX(RowInid) FROM myTable GROUP BY ID, VALUE
EDIT:
As you updated your question, you can get value field using sub-query like this:
SELECT ID, VALUE, RowInid
FROM myTable t1 WHERE RowInid =
(
SELECT MAX(RowInid) FROM myTable WHERE id = t1.id GROUP BY id
)
ORDER BY id ASC;
You can also achieve this using INNER JOIN like this:
SELECT t2.ID, VALUE, t2.RowInid FROM myTable t1
INNER JOIN
(
SELECT ID, MAX(RowInid) AS RowIniD FROM myTable GROUP BY ID
) AS t2
ON t1.ID = t2.ID AND t1.RowInid = t2.RowInid
ORDER BY t1.ID ASC;
See this SQLFiddle
See more about GROUP BY and MAX in SQL Server.
no need for group by or max at all
select id, value, rowinid from
( select *, row_number() over (partition by id, order by rowinid desc) rn from yourtable ) v
where rn = 1
Try with,
Use Sub Query to get Id, Value and Max RowInid,
SELECT m1.[Id],m1.Value, m1.RowInid
FROM [Practice].[dbo].[myTable] m1 WHERE RowInid = (SELECT MAX(m2.RowInid) FROM [Practice].[dbo].[myTable] m2 WHERE M1.Id = m2.Id GROUP BY Id)
above query return result like:
4-xx-2
3-xx-1
2-xx-2
1-xx-3
To Ascending this use,
SELECT m1.[id],m1.Value, m1.RowInid
FROM [Practice].[dbo].[myTable] m1 WHERE m1.RowInid = (SELECT MAX(m2.RowInid) FROM [Practice].[dbo].[myTable] m2 WHERE M2.id = m1.id GROUP BY id) ORDER BY m1.id ASC