Sum up delivered companies for every customer(ID) - sql-server

I'm back in action ;) This time I have a pretty heavy task (I think).
Here's what I got:
|customerID ||company |compdel |Street |Code |Date 1 |Date 2 |
+-------------------------------+--------------------------------------+
|1 ||Example1 |DELExam1|ABC Rd.1|4025 |01.01.2015 |01.08.2015 |
|1 ||Example1 |DELExam1|ABC Rd.1|4025 |13.04.2015 |01.12.2015 |
|1 ||Example1 |DELExam2|DEL St.1|0212 |13.03.2015 |09.07.2015 |
|1 ||Example1 |DELExam3|REF Wy.1|9875 |26.05.2015 |16.09.2015 |
|2 ||Example2 |DELExam4|REG St.1|6754 |21.02.2015 |16.05.2015 |
|2 ||Example2 |DELExam5|HIO Wy.1|9999 |01.03.2015 |06.08.2015 |
|2 ||Example2 |DELExam5|HIO Wy.1|9999 |01.01.2015 |06.02.2015 |
I want to show for every customerID every delivered company (compdel) summed in one line with the earliest date in Date 1 and the newest Date in Date 2. To make it easier to understand, I want this result:
|customerID ||company |compdel |Street |Code |Date 1 |Date 2 |
+-------------------------------+--------------------------------------+
|1 ||Example1 |DELExam1|ABC Rd.1|4025 |01.01.2015 |01.12.2015 |
|1 ||Example1 |DELExam2|DEL St.1|0212 |13.03.2015 |09.07.2015 |
|1 ||Example1 |DELExam3|REF Wy.1|9875 |26.05.2015 |16.09.2015 |
|2 ||Example2 |DELExam4|REG St.1|6754 |21.02.2015 |16.05.2015 |
|2 ||Example2 |DELExam5|HIO Wy.1|9999 |01.01.2015 |06.08.2015 |
I tried it already with this select-Statement but it won´t work: I know, that this can only be a part of the answer....
SELECT *
FROM
(SELECT
customerID, company, compdel, Street, Code, Date 1, Date 2,
ROW_NUMBER() OVER(PARTITION BY compdel ORDER BY customerID) rn
FROM
table 1) as Y
WHERE
rn = 1

Use GROUP BY with distinct values (customerId, company etc.) and MIN and MAX for dates
SELECT CustomerId
, Company
, CompDel
, Street
, Code
, MIN(Date1) As EarliestDate1
, MAX(Date2) AS NewestDate2
FROM YourTable
GROUP BY CustomerId, Company, CompDel, Street, Code

Related

How to : update column with sum column in same table in SQL Server 2014?

Before table data:
-----------------------
|ID |WORK|VALUE|TOTAL|
-----------------------
|ID1|WRITE |10 | |
|ID1|TYPE |5 | |
|ID2|READ |25 | |
|ID2|SCAN |30 | |
|ID3|PRINT |15 | |
|ID4|SETTING|20 | |
|ID5|REPAIR |5 | |
|ID5|MAINTE |25 | |
|ID5|MONITOR|20 | |
Total is sum value from same id
ID1 10+5
ID2 25+30
ID3 15
ID4 20
ID5 50
For now I use the insert method with create table data2 (ID,TOTAL)
INSERT INTO DATA2(DATA2.ID, DATA2.TOTAL)
SELECT DATA.ID, SUM (DATA.VALUE) AS TOTAL
FROM DATA
GROUP BY DATA.ID
Then I do SELECT JOIN FROM DATA2 AND DATA
After table data
-----------------------
|ID |WORK|VALUE|TOTAL|
-----------------------
|ID1|WRITE |10 |15 |
|ID1|TYPE |5 |15 |
|ID2|READ |25 |55 |
|ID2|SCAN |30 |55 |
|ID3|PRINT |15 |15 |
|ID4|SETTING|20 |20 |
|ID5|REPAIR |5 |50 |
|ID5|MAINTE |25 |50 |
|ID5|MONITOR|20 |50 |
To update the value total to table, you need to have the column..
alter table tblname
add total int
If this is not a one time approach,i would recommend creating a view like below
create view somename
as
select id,work,value,
sum(value) over (partition by id ) as total
from tabel
if you want to update table as one time excercise
;with cte
as
(select id,work,value,
sum(value) over (partition by id ) as total1
from tablename
)
update t
set t.total=c.total1
from cte c
join tablename t
on t.id=c.id
Another way to update the total.
UPDATE T1
SET T1.TOTAL=T2.TOTAL
FROM YOUT_TABLE T1
JOIN (
SELECT ID,SUM(VALUE) AS TOTAL
FROM YOUR_TABLE
GROUP BY ID
) T2 ON T1.ID=T2.ID
DEMO

How to get latest salary of each associate in sql, table have month and year column also. each associate have minimum 4 to 5 records

Here is my query
Select distinct ASSOCIATE_ID,
Rate_Billed,
Currency,
RateMultiplier,
UOM,
MONTH,
YEAR= MAX(YEAR) over (partition by associate_id)
from asso_billinghrs
Below is the sample data.
|ASSOCIATE_ID |Rate_Billed | Currency| RateMultiplier| UOM |MONTH|YEAR|
|---------------|------------|----------|-----------------|-----|-----|----|
|1 |23.78 |USD |1 |B |11 |2013|
|1 |23.78 |USD |1 |B |2 |2014|
|1 |23.78 |USD |1 |B |3 |2014|
|2 |1 |INR |0.0146701 |C |1 |2017|
|2 |1 |INR |0.0147451 |C |1 |2017|
Below is the output
|ASSOCIATE_ID| Rate_Billed|Currency|RateMultiplier|UOM|MONTH|YEAR|
|------------|-------------|--------|--------------|---|-----|----|
|1 |23.78 |USD |1 |B |3 |2014|
|2 |1 |INR |0.0147451 |C |1 |2017|
Get latest salary of each associate in sql table having month and year column also. Each associate have minimum 4 to 5 records
Thanks
Try this :
WITH CTE AS(
Select distinct ASSOCIATE_ID,
Rate_Billed,
Currency,
RateMultiplier,
UOM,
MONTH,
YEAR,
ROW_NUMBER()over (partition by associate_id ORDER BY [YEAR],[MONTH] DESC) RN
from asso_billinghrs)
SELECT *
FROM CTE
WHERE RN=1
You may try using RANK() to get the following output.
select * from
(select *,RANK() over(partition by ASSOCIATE_ID order by tblyear desc,tblmonth desc,ratemultiplier desc)as r from asso_billinghrs)T
where r = 1
Output:
|ASSOCIATE_ID| Rate_Billed|Currency|RateMultiplier|UOM|MONTH|YEAR|
|------------|-------------|--------|--------------|---|-----|----|
|1 |23.78 |USD |1 |B |3 |2014|
|2 |1 |INR |0.0147451 |C |1 |2017|
FIDDLE

Using MAX in WHERE Clause with < -Operator

I want to select the entries in a table when the registration adress is equal to one (of more than one) delivery adresses AND this adress is the adress where the customer sent all his orders to this adress, since the adress was created.
Date 1 = Date of first order to specific adress, Date 2 = Last/Newest Order to specific adress.To make iot easier to understand... I´ve got this (Table1):
The task:
|cID ||company|Street |Code|del |Street2 |Cod2|Date 1 |Date 2 |
+------------------------------------------------------------------------+
|1 ||Ex1 |ABC Rd.1|4025|Ex1 |DEL St.1|0212|01.01.2015|06.03.2015|
|1 ||Ex1 |ABC Rd.1|4025|Ex1 |REF Wy.1|9875|26.02.2015|16.05.2015|
|1 ||Ex1 |ABC Rd.1|4025|Ex1 |ABC Rd.1|4025|13.06.2015|08.08.2015|
|2 ||Ex2 |HIO Wy.1|9999|Ex2 |DEL St.1|0212|13.03.2015|09.07.2015|
|2 ||Ex2 |HIO Wy.1|9999|Ex2 |REG St.1|6754|21.02.2015|16.05.2015|
|2 ||Ex2 |HIO Wy.1|9999|Ex2 |BLA Rd.5|0897|01.03.2015|06.12.2015|
|2 ||Ex2 |HIO Wy.1|9999|Ex2 |HIO Wy.1|9999|09.10.2015|26.11.2015|
|3 ||Ex3 |REG St.1|1114|Ex3 |DEL St.9|0212|13.01.2015|09.02.2015|
|3 ||Ex3 |REG St.1|1114|Ex3 |REG St.1|6754|21.03.2015|16.09.2015|
|3 ||Ex3 |REG St.1|1114|Ex3 |BLA Rd.5|0897|08.06.2015|06.08.2015|
|4 ||Ex4 |FAR RD.9|4567|Ex4 |DDR Wy.2|0897|01.03.2015|06.12.2015|
|4 ||Ex4 |FAR RD.9|4567|Ex4 |FAR RD.9|4567|09.10.2015|26.12.2015|
Expected Result
|cID ||company|Street |Code|del |Street |Code|Date 1 |Date 2 |
+------------------------------------------------------------------------+
|1 ||Ex1 |ABC Rd.1|4025|Ex1 |ABC Rd.1|4025|13.06.2015|08.08.2015|
respectively cID = 1
Here´s what I tried so far, but it´s not working....
SELECT cID
FROM Table1
WHERE company= del
AND Street = Street2
AND Code = Cod2
AND (SELECT MAX (Date 1) > (=! MAX(Date2) FROM Table1 Group by CID)
Edit (To make it more simple to understand):
e.g. the company with the name Ex1 (cID 1) is now located in ABC Rd.1|4025 (actual adress - the adress before is unknown) and has 3 adresses in system, where the orders of the company has been send to.
The first order on adress 1 (DEL St.1|0212) was on 01.01.2015,
the last order to this adress was on 06.03.2015.
The first order on adress 2 (REF Wy.1|9875) was on 26.02.2015
and the last order to this adress was on 16.05.2015 ...
-> I want the cID´s where registration adress (actual adress of the company) is the actual and only delivery adress.
Try using row number to get the latest date.
SELECT *
FROM (
SELECT *, ROW_NUMBER() OVER ( PARTITION BY Street, Code, company
ORDER BY Date1 DESC) as rn
FROM Table1
WHERE Street = Street2
AND Code = Cod2
AND company = del
) T
WHERE T.rn = 1
This should work:
SELECT cID
FROM Table1
WHERE Street = Street2
AND Code = Cod2
AND Date1 > (
SELECT MAX(Date2)
FROM Table1 as delivery
WHERE Table1.cID = delivery.cID
AND (delivery.Street2 <> Street OR delivery.Cod2 <> Code)
)
The subquery must itself be a correct SELECT-FROM-WHERE query, and a variable must be used to disambiguate between the outer and inner tables. The inner query selects all deliveries made to the same company but excluding the current delivery, and picks the maximal most recent date. It is then compared to the oldest date of the current delivery address.
Note that the data is not in second normal form. It may be worth, depending on the use case, splitting the table into a table with companies and a table with deliveries.
On my side, it returns 1 as expected.

How to get the count of each distinct value in Multiple columns and get the result in separate columns?

I need the following table to be queried to get the result given below the table.
Table:
----------------------------------
| Name | Age | slot |
|-------|--------|---------------|
|A |20 | 1 |
|B |30 | 2 |
|C |30 | 1 |
|D |20 | 1 |
|E |40 | 2 |
|F |40 | 3 |
|G |50 | 3 |
----------------------------------
Result:
-------------------------------------------
|Age |Age_Count |Slot |Slot_Count|
-------------------------------------------
|20 | 2 |1 |3 |
-------------------------------------------
|30 | 2 |2 |2 |
-------------------------------------------
|40 | 2 |3 |2 |
-------------------------------------------
|50 | 1 |
-----------------------
While searching stackoverflow i found this question for single column question and there is [this link for multiple columns] (get the count of each distinct value in "Multiple" columns) question. The answers from the second link (for the multiple coulmn's distinct count) is displayed under a single column and my requirement is i guess quite different from the answers posted there.
Thanks in advance
Your request is kind of odd. Are you sure you want that?
If so, this may help:
SET #x:=0,#y:=0,#m:=0,#n:=0;
SELECT
DISTINCT age,age_count, slot,slot_count
FROM (
SELECT
age, age_count, slot, slot_count
FROM (
SELECT
#x:=#x + 1 AS aid, age, COUNT(*) age_count
FROM
slots
GROUP BY age
) a
LEFT JOIN (
SELECT
#y:=#y + 1 AS sid, slot, COUNT(*) slot_count
FROM
slots
GROUP BY slot
) s ON a.aid = s.sid
UNION
SELECT
age, age_count, slot, slot_count
FROM (
SELECT
#m:=#m + 1 AS aid, slot, COUNT(*) slot_count
FROM
slots
GROUP BY slot
) a
LEFT JOIN (
SELECT
#n:=#n + 1 AS sid, age, COUNT(*) age_count
FROM
slots
GROUP BY age
) s ON a.aid = s.sid
) a
If you know for sure that you have more unique ages than unique slots , or opposite, you can get ride of messy union.

How to exclude rows for the same ID based on Category and Date

+--+-------+----------+---+
|ID|OrderID|OrderDate |Cat|
+--+-------+----------+---+
|1 |240904 |23/05/2013|63 |
+--+-------+----------+---+
|1 |338584 |11/12/2013|64 |
+--+-------+----------+---+
|1 |47309 |21/11/2011|64 |
+--+-------+----------+---+
|2 |175307 |23/11/2012|63 |
+--+-------+----------+---+
+--+-------+----------+---+
|2 |195307 |24/12/2012|64 |
+--+-------+----------+---+
+--+-------+----------+---+
|2 |175300 |23/11/2011|63 |
+--+-------+----------+---+
+--+-------+----------+---+
|5 |175307 |23/11/2012|63 |
+--+-------+----------+---+
+--+-------+----------+---+
|5 |215307 |15/1/2013|64 |
+--+-------+----------+---+
+--+-------+----------+---+
|7 |195307 |15/06/2012|63 |
+--+-------+----------+---+
I'm using SQL Server 2008 R2. I trying (struggling) to find a way to get more recent OrderDate for Cat 64 then Cat 63 for on the same ID all from the table that looks as those records separated by | above.
Try Like this
Select OrderID,OrderDate From
(
Select *,ROW_NUMBER() over(PARTITION by ID,CAT Order by OrderDate DESC) AS RN
From tbl
) AS Tmp
Where RN = 1
Working Fiddle

Resources