SQL - How to select row by compare date from 2 table - sql

I have 2 table like that:
Table1:
ID | COMPANY_NAME | Rank | FIRST_REGIST_DATE
1 A 1 2017-09-01
2 B 2 2017-09-05
Table 2:
ID | COMPANY_NAME | RANK | FIRST_REGIST_DATE
1 A 3 2017-09-03
2 C 4 2017-09-04
I need to SELECT company with the data FIRST_REGIST_DATE and RANK
In case of company have 2 first regist date, we choose the earlier date and RANK greater
(EX: company A above will have first date: 2017-09-01)
The Expect result will like that:
Company A - Rank 3 - Date:2017-09-01
Please have me to SELECT in that case

This technically answers the question but avoids the elephant in the room (which ID takes preference?). As both tables have ID's that may overlap ({B,C} have an ID of 2) rules need to be defined as to which ID takes preference what will the other table ID's be renamed to.
Select COMPANY_NAME
,MIN(FIRST_REGIST_DATE) as REGIST_DATE
from (
SELECT *
FROM #table1
UNION ALL
SELECT *
FROM #table2
) t3
Group by COMPANY_NAME
OP dont change your question (by adding RANK) after the question has been answered.
For your changes: kindly contributed by #toha
Select COMPANY_NAME
,MIN(FIRST_REGIST_DATE) as REGIST_DATE
,MAX(RANK ) as RANK
from ( SELECT *
FROM #table1
UNION ALL
SELECT *
FROM #table2 ) t3
Group by COMPANY_NAME

If I understand the question correctly you have two tables with data containing company details and first registration date and you want to show the row with the earliest first registration date. The following query will help you.
SELECT company_name, MIN(fisrt_regist_date)
(
SELECT company_name, fisrt_regist_date
FROM table1
UNION ALL
SELECT company_name, fisrt_regist_date
FROM table2
) tab1
FROM tab1
GROUP BY company_name
The above query will combine the results of the first table and the second table and then show you the details of the company along with the oldest registration date.

Related

Select single first occurrence of row against distinct local ID from a table and insert it in another table

I want a postgre SQL query that selects only first row from table against distinct LocalID and enter the result in another table.
Records:
ID| LocalID| Name
1 233 Tim
2 633 John
3 633 Alex
4 234 Mike
5 233 Dave
6 556 Kim
Wanted result:
ID| LocalID| Name
1 233 Tim
2 633 John
4 234 Mike
6 556 Kim
I tried using
CREATE TABLE Weeklylist AS (select distinct on (localid) * from Monthlylist)
But this query select the last distinct record and enters it into the table. All i want is the first occurrence of the row containing distinct localID should be entered in the table.
The use of distinct on in your existing statement indicates that you are using Postgres.
The problem with your query is that it is missing an ORDER BY clause. Without it, it is undefined which record will be selected (you are seeing the last record being picked, but this is not guaranteed to be consistent over subsequent executions of the same query). So, add the ORDER BY clause:
create table Weeklylist as
select distinct on (localid) * from Monthlylist order by localid, id
Side note: parentheses around the select statement are superfluous here.
You can use DISTINCT ON in PostgreSQL :
CREATE TABLE Weeklylist
AS
SELECT DISTINCT ON (LocalID) *
FROM Monthlylist ml
ORDER BY LocalID, ID -- Missing in your query
In MySQL older version correlated sub-query is one way :
SELECT ml.*
FROM Monthlylist ml
WHERE ml.id = (SELECT MIN(ml1.id) FROM Monthlylist ml1 WHERE ml1.LocalID = ml.LocalID);
This will give you what you need:
select *
from Monthlylist
where id in (
select min(id)
from Monthlylist
group by localid
)
create table WeeklyList as
select *
from Monthlylist
where id in (
select min(id)
from Monthlylist
group by localid
)
Demo on DB Fiddle
You need a subquery and join to get your desired output.
create table Weeklylist AS (
select t.* from Monthlylist t
inner join (select distinct on (localid) * from Monthlylist) t1 on t1.localid = t.localid and t.id = t1.id
order by id, localid)
see sqlfiddle

totalling rows for distinct values in SQL

I haven't had much experience with SQL and it strikes me as a simple question, but after an hour of searching I still can't find an answer...
I have a table that I want to add up the totals for based on ID - e.g:
-------------
ID Quantity
1 30
2 11
1 4
1 3
2 17
3 16
.............
After summing the table should look something like this:
-------------
ID Quantity
1 37
2 28
3 16
I'm sure that I need to use the DISTINCT keyword and the SUM(..) function, but I can only get one total value for all unique value combinations in the table, and not separate ones like above. Help please :)
Select ID, Sum(Quantity) from YourTable
Group by ID
You can find here some resources to learn more about "Group by": http://www.w3schools.com/sql/sql_groupby.asp
SELECT ID, SUM(QUANTITY) FROM TABLE1 GROUP BY ID ORDER BY ID;
Select ID, Sum(Quantity) AS Quantity
from table1
Group by ID
Replace table1 with name of the table.
Just posting a complete answer that aliases the column and orders the results:
SELECT ID, SUM(Quantity) as [Quantity]
FROM TableName
GROUP BY ID
ORDER BY ID

Selecting distinct values from table using two columns

I have following data in the table.
Id Name
1 Abc
2 Abc
3 Xyz
4 Xyz
5 def
6 def
I want following results from the query
Id Name
1 Abc
2 Xyz
3 def
I want to avoid duplicates in the name column.
Any help is greatly appreciated.
Select distinct
id, name
from table A
will not work as ids are having a different values.
Use a group by instead.
select
min(id), [name]
from
tableA
group by [name]
Note that in your example, the ids that corresponds with Xyz are 3 and 4, so getting a 2 next to Xyz is only possible if you break the integrity of the table. If you are just looking for an auto number next to the ids you can do this:
SELECT row_number() OVER (ORDER BY min(id)) id,
name
FROM tableA
group by name
You can get your specific result using:
select row_number() over (order by min(id)) as id, name
from table A
group by name;
Renumbering the rows seems strange, but row_number() will do that.

Select particular not grouped column from grouped set

The topic might be a little bit unclear but I couldn't describe in a single sentence what I want to achieve.
Say I have a table that is (columns)
id INT PK
name VARCHAR
date DATE
I have a grouping select
select
name,
max(date)
from table
group by name
that gives me a name and the latest date.
What is the easiest way to join the id column to the current aggregated result set with the id value where the date was the maximum?
Let me explain what my goal is with an example:
The table is filled with the data as follows
id name date
1 david 2012-12-12
2 david 2013-12-02
3 patrick 2014-01-02
4 patrick 2012-11-11
and by my query I'd like to get the following result
id name date
2 david 2013-12-02
3 patrick 2014-01-02
Notice that all the records for name = 'david' are aggregated and the maximum date is selected. How to get the row id for this maximum date?
One option is to use ROW_NUMBER():
SELECT id, name, date
FROM (
SELECT id, name, date,
row_number() over (partition by name order by date desc) rn
FROM yourtable
) t
WHERE rn = 1
SQL Fiddle Demo
Another option is to join the table back to itself using the MAX() aggregate. This option could potentially result in ties if multiple id/name combinations share the same max date:
SELECT t.id, t.name, t.date
FROM yourtable t
JOIN (SELECT name, max(date) maxdate
FROM yourtable
GROUP BY name) t2 on t.name = t2.name AND t.date = t2.maxdate
More Fiddle

Fetch Max from a date column grouped by a particular field

I have a table similar to this:
LogId RefId Entered
==================================
1 1 2010-12-01
2 1 2010-12-04
3 2 2010-12-01
4 2 2010-12-06
5 3 2010-12-01
6 1 2010-12-10
7 3 2010-12-05
8 4 2010-12-01
Here, LogId is unique; For each RefId, there are multiple entries with timestamp. What I want to extract is LogId for each latest RefId.
I tried solutions from this link:http://stackoverflow.com/questions/121387/sql-fetch-the-row-which-has-the-max-value-for-a-column. But, it returns multiple rows with same RefId. The LogId as well as RefId should be unique.
Can someone help me with this?
Thanks
Vamyip
You need to use a subquery that extracts the latest Entered value for each RefId, and then join your source table to this on RefId, Entered:
SELECT DISTINCT MyTable.LogId, MyTable.Entered FROM MyTable
INNER JOIN (SELECT RefId, MAX(Entered) as Entered FROM MyTable GROUP BY RefId) Latest
ON MyTable.RefId = Latest.RefId AND MyTable.Entered = Latest.Entered
Since it appears auto-increment log ID, they would be date/time stamped in sequential order. So, by grabbing the last LogID per Reference ID, you'll have the "most recent" one in the "PreQuery" below, then join based on that single ID to the original table to get the actual date stamp info (or other details) you need from the actual log.
select PreQuery.RefID,
PreQuery.LastLogEntry,
L.Entered
from
( select RefID,
Max( LogID ) LastLogEntry
from
YourLog
group by
RefID ) PreQuery,
YourLog L
where
PreQuery.LastLogEntry = L.LogID
To handle the duplicates correctly:
SELECT m.*
FROM (
SELECT DISTINCT refid
FROM mytable
) md
JOIN mytable m
ON m.LogID =
(
SELECT LogID
FROM mytable mi
WHERE mi.refid = md.refid
ORDER BY
mi.refid DESC, mi.entered DESC, mi.logid DESC
LIMIT 1
)
Create an index on mytable (refid, entered, logid) for this to work fast.