Combine two order by queries to get result - mysql

I have two queries :
SELECT COUNT(*) as adet, MONTHNAME(date_created) as monthname
FROM orders
WHERE YEAR(date_created) = 2017
GROUP BY MONTH(date_created)
which returns this result
adet monthname
----------------
17 January
24 February
45 March
40 April
and another query :
SELECT COUNT(*) as adet, seller_id
FROM orders
WHERE YEAR(date_created) = 2017
GROUP BY seller_id
which returns this result :
adet seller_id
---------------
120 20
120 21
500 22
400 23
How can I combine those two queries to get the result like this:
adet month seller_id
--------------------
-09- -Jan- --20--
-05- -Fab- --20--
-05- -Mar- --20--
...
-05- -jan- --21--
-04- -Fab- --21--
...
-05- -jan- --22--
-04- -Fab- --22--

You can try
SELECT COUNT(*) adet, LAST_DAY(date_created) month_ending, seller_id
FROM orders
WHERE date_created >= DATE_FORMAT(CURDATE(),'%Y-01-01')
AND date_created < DATE_FORMAT(CURDATE(),'%Y-01-01') + INTERVAL 1 YEAR
GROUP BY LAST_DAY(date_created), seller_id
Why would you use something so seemingly complex? Because
it will work next year.
it will handle ranges of dates which don't end on year boundaries
it will be able to use an index on your date_created column and therefore run faster.

Try below query:
SELECT COUNT(*) as adet, MONTHNAME(date_created) as monthname,seller_id
FROM orders where YEAR(date_created) = 2017
GROUP BY MONTH(date_created),seller_id

Related

Calculating aggregated number of days in each month in sql

I've got a table with multiple columns and two of the columns are start_date and end_date.
I need to calculate the number of days in each month. Let's assume I have following data in my table
id | start_date | end_date
1 04.01.2016 15.02.2016
2 07.01.2016 22.01.2016
3 16.05.2016 11.07.2016
I want an output as follows
Month | numberOfTravelDays
January 51
February 15
May 15
June 31
July 11
This output I am expecting is the number of total travel days each month has been utilized. I am having trouble constructing the sql query for this. Can someone assist me on this?
This is what I have for now. And it's not doing the job. The below query also filters only this year's records(but ignore that).
select MONTH(start_date) as month,
COUNT(DATEDIFF(start_date, end_date)) as numberOfTravelDays
from travel
where YEAR(start_date) = YEAR(CURDATE())
group by MONTH(start_date),
MONTH(end_date)
Use a derived table:
select monstart,
sum(datediff(least(m.monend, t.end_date) + interval 1 day,
greatest(m.monstart, t.start_date)
)
) as days_worked
from travel t join
(select date('2016-01-01') as monstart, date('2016-01-31') as monend union all
select date('2016-02-01') as monstart, date('2016-02-29') as monend union all
. . .
) m
on t.end_date >= m.monstart and t.start_date <= m.monend
group by monstart;

I need to join two table in mysql

I need some help to solve an issue with my query. I want to join the output of two select statements:
1st
select extract(year from createdDate) as year,
count(extract(year from createdDate)) as count
from table
where to_user_id= 322
group by extract(year from createdDate);
and its output
Year Count
2014 18
2015 117
2016 9
and 2nd query
select count(extract(year from createdDate)) as count
from table
where userId=322
group by extract(year from createdDate);
and its output
Count
18
110
11
I want to add this two tables into one table.
I want that type of output,
Year Count Count
2014 18 18
2015 117 110
2016 9 11
Note that I use to_user_id in query 1 but userId in query 2.
I tried to solved out this thing but I got repeated values in the output.
Anyone know the solution?
Write them as subqueries and join them together.
SELECT a.year, a.count AS t_user_count, b.count AS user_count
FROM (select YEAR(create_date) AS year, COUNT(*) AS count
FROM table
WHERE to_user_id = 322
GROUP BY year) AS a
JOIN (SELECT YEAR(create_date) AS year, COUNT(*) AS count
FROM table
WHERE user_id = 322
GROUP BY year) AS b
ON a.year = b.year

MySQL calculate gain, loss and net gain over a period of time

I have a table something like this:
id | Customer | date
-----------------------------------------
1 | Customer2 | 2013-08-01 00:00:00
-----------------------------------------
2 | Customer1 | 2013-07-15 00:00:00
-----------------------------------------
3 | Customer1 | 2013-07-01 00:00:00
-----------------------------------------
. | ... | ...
-----------------------------------------
n | CustomerN | 2012-03-01 00:00:00
I want to calculate the "gained" customers for each month, the "lost" customers for each month and the Net Gain for each month, even if done in separate tables / views.
How can I do that?
EDIT
Ok, let me demonstrate what I've done so far.
To select Gained customers for any month, I've tried to select customers from Bookings table where the following not exist:
select Customer
from Bookings
where not exists
(select Customer
from Bookings
where
(Bookings.date BETWEEN
DATE_FORMAT(DATE_SUB(Bookings.date, INTERVAL 1 MONTH), '%Y-%m-01 00:00:00')
AND DATE_FORMAT(Bookings.date, '%Y-%m-01 00:00:00'
)
) AND Bookings.date >= STR_TO_DATE('2010-11-01 00:00:00', '%Y-%m-%d 00:00:00'))
This supposedly gets the customers that existed in the "selected" month but not in the previous one. "2010-11-01" is the date of the start of bookings + 1 month.
To select Lost customers for any month, I've tried to select customers from Bookings table where the following not exist:
select Customer
from Booking
where not exists
(select Customer
from Bookings
where
(Bookings.date BETWEEN
DATE_FORMAT(Bookings.date, '%Y-%m-01 00:00:00')
AND Bookings.date
)
AND Bookings.date >= STR_TO_DATE('2010-11-01 00:00:00', '%Y-%m-%d 00:00:00'
)
)
This supposedly gets the customers that existed in a previous month but not in the "selected" one.
For the "Loss" SQL query I got empty result! For the "Gain" I got thousands of rows but not sure if that's accurate.
You can use COUNT DISTINCT to count your customers, and WHERE YEAR(Date) = [year] AND MONTH(Date) = [month] to get the month.
The total number of customers in Sept 2013:
SELECT COUNT(DISTINCT Customer) AS MonthTotalCustomers FROM table
WHERE YEAR(date) = 2013 AND MONTH(date) = 9
The customers gained in Sept 2013:
SELECT COUNT(DISTINCT Customer) AS MonthGainedCustomers FROM table
WHERE YEAR(date) = 2013 AND MONTH(date) = 9
AND Customer NOT IN
(SELECT Customer FROM table
WHERE date < '2013-09-01')
Figuring out the lost customers is more difficult. I would need to know by what criteria you consider them to be 'lost.' If you just mean that they were around in August 2013 but they were not around in September 2013:
SELECT COUNT(DISTINCT Customer) AS MonthLostCustomers FROM table
WHERE YEAR(date) = 2013 AND MONTH(date) = 8
AND Customer NOT IN
(SELECT Customer FROM table
WHERE YEAR(date) = 2013 AND MONTH(date) = 9)
I hope from these examples you can extrapolate what you're looking for.

SQL to return record counts in X intervals

I have a table like this:
id | created_on
1 2013-09-03 20:05:09
2 2013-09-05 17:03:13
...
How do I write a query to return a result of record counts that was created from Date X to Date Y in 7-day intervals?
So the result would look like this:
count | created_on
4 2013-09-17 00:00:00
2 2013-09-24 00:00:00
1 2013-09-31 00:00:00
10 2013-10-07 00:00:00
...
You can go to the beginning of the week by subtracting the day of the week. Here is one way to do that:
select date(created_on - interval dayofweek(created_on) day), count(*)
from t
group by date(created_on - interval dayofweek(created_on) day);
If this is not the day you want the week to start, then you can add an offset day.
Group by the date field, floored to the week:
SELECT
count(*),
YEARWEEK(created_on) as week
FROM
yourtable
GROUP BY week
This assumes that created_on is a type that can be interpreted as a date:
http://dev.mysql.com/doc/refman/5.5/en/date-and-time-functions.html#function_yearweek
This will get you weekly groupings, but you may want to then convert that field (which will look like YYYYWW) back to something more readable.
You can try this
SELECT created_on, count( id ) AS count
FROM `test_table`
WHERE created_on
BETWEEN '2013-09-01'
AND '2013-10-10'
GROUP BY WEEK( created_on )

MySQL Selecting MAX total with date and ID

I have a cron script that writes the total number of active users to a table every day. I'm trying to now generate a simple report that would show the "high water mark" for each month. Because some accounts expire during the month it's possible the highest number may NOT be at the end of the month.
Here's a sample of my table structure
tblUserLog
-----------
record_id INT(11) // PRIMARY KEY
run_date DATE // DATE RUN
ttl_count INT(11) // TOTAL FOR DAY
Sample data:
record_id run_date ttl_count
1 2013-06-01 500
2 2013-06-10 510
3 2013-06-20 520
4 2013-06-30 515
5 2013-07-01 525
6 2013-07-10 530
7 2013-07-20 540
8 2013-07-31 550
9 2013-08-01 560
What I would like returned is:
record_id run_date ttl_count
3 2013-06-20 520
8 2013-07-31 550
9 2013-08-01 560
I've tried two queries that are close...
// This will give me the total for the first of the month
SELECT s.record_id, s.run_date, s.ttl_count
FROM tblStatsIndividual s
JOIN (
SELECT record_id
FROM tblStatsIndividual
GROUP BY DATE_FORMAT(run_date, '%Y %m')
HAVING MAX(ttl_count)
) s2
ON s2.record_id = s.record_id
ORDER BY run_date DESC
This returns the total for the first of each month, along with the record_id and correct date for the total.
Tried this...
SELECT record_id,max(run_date), max(ttl)
FROM (
SELECT record_id,run_date, max(ttl_count) AS ttl
FROM tblStatsIndividual
GROUP BY DATE_FORMAT(run_date, '%Y %m')
) a
GROUP BY DATE_FORMAT(run_date, '%Y %m')
ORDER BY run_date DESC
This one appears to get the correct "high water mark" but it's not returning the record_id, or the run_date for the row that IS the high water mark.
How do you get the record_id and the run_date for the highest total?
Something like
Select detail.Record_ID, detail.Run_Date, detail.ttl_Count
From tblStatsIndividual detail
Inner Join
(Select Year(run_date) as Year, Month(Run_date) as Month, Max(ttl_count) as ttl
From tblStatsIndividual
Group By Year(run_date), Month(Run_date)) maximums
On maximums.Year = Year(detail.Run_date) and maximums.Month = Month(detail.Run_date)
and maximums.ttl = detail.ttl_count
Should do it. NB based on your requirement if you had two records in the same month with the same (and highest in the month) ttl_count, they would both be returned.
Based on the help from #Tony Hopkinson, This query gets me the info. The one caveat is it shows the ID and date for the first occurrence of the MAX total, so if the total is the same three days in a row on a month, the first day's ID is returned. For my purpose, the last ID would be more ideal, but I can live with this:
SELECT s.Record_ID, s.Run_Date, s.ttl_Count
FROM tblStatsIndividual s
INNER JOIN (
SELECT YEAR(run_date) AS yr, MONTH(run_date) AS mon, MAX(ttl_count) AS ttl
FROM tblStatsIndividual
GROUP BY DATE_FORMAT(run_date, '%Y %m')
) maximums
ON maximums.yr = YEAR(s.run_date)
AND maximums.mon = MONTH(s.run_date)
AND maximums.ttl = s.ttl_Count
GROUP BY ttl_count
ORDER BY run_date DESC