dbTalk Databases Forums  

Aggregating Data - Sum(year), Count(year), Sum(month), Count(month), Sum(today), Count(today)

mailing.database.mysql mailing.database.mysql


Discuss Aggregating Data - Sum(year), Count(year), Sum(month), Count(month), Sum(today), Count(today) in the mailing.database.mysql forum.



Reply
 
Thread Tools Display Modes
  #1  
Old   
crane.jake@gmail.com
 
Posts: n/a

Default Aggregating Data - Sum(year), Count(year), Sum(month), Count(month), Sum(today), Count(today) - 10-27-2006 , 11:52 PM






Hi, I'm trying to find the following information from the table found
bellow.

Year_Sales - # of sales that have occurred this year
Year_Income - SUM(amount)
Month_Sales - # of sales that have occurred this month
Month_Income - SUM(amount)
Today_Sales -- # of sales that have occurred today
Today_Icome - SUM(amount)

My table looks like this (simplified):

CREATE TABLE ` Transaction` (
`id` int(10) unsigned NOT NULL auto_increment,
`date_time` datetime NOT NULL,
`user_id` int(10) unsigned NOT NULL,
`amount` int(10) unsigned NOT NULL default '0',
PRIMARY KEY (`id`),
KEY (`date_time `),
KEY `userId` (`userId`),
) ENGINE=InnoDB DEFAULT CHARSET=latin1 |

I'm working on a site that allows people to sell stuff and every time
a seller checks his account he'll see a report showing his
year_sales, year_income, month_sales, etc. Since this query will be
run fairly regularly I'm trying to build this query as efficient as
possible. Also over time the Transaction table will get quite big,
well hopefully J

So far here are the solutions I came up with.

1) Run three queries, (Q1) get year_* info, (Q2) get month_* info,
(Q3) get today_* info. Each query will use where date = .... clauses
to limit the date range accordingly. This feels like a horrible
solution.

2) Use temporary tables

a) Place the results from (Q1) into a temporary table (TQ1), find
year_sales and year_income
b) (Q2) will now query from the temporary table (TQ1) to create a new
temporary table (TQ2), then find month_sales, month_income.
c) (Q3) will now query from the temporary table (TQ2), find
today_sales, today_income.
d) Remove (TQ1), (TQ2)
This solution seems a bit better, but still doesn't feel right.

3) If there is a way to subquery your first

I'm open to suggestions! Thanks in advance

Jake


Reply With Quote
  #2  
Old   
shakahshakah@gmail.com
 
Posts: n/a

Default Re: Aggregating Data - Sum(year), Count(year), Sum(month), Count(month), Sum(today), Count(today) - 10-28-2006 , 09:39 AM






The syntax may be off as this is from another DB system, but something
along the lines of the following might work for you, or at least give
you some ideas:

SELECT user_id
,SUM(
CASE WHEN date_time >= date_trunc('year',now()) THEN 1
ELSE 0
END
) AS sales_this_year
,SUM(
CASE WHEN date_time >= date_trunc('year',now()) THEN amount
ELSE 0
END
) AS income_this_year
,SUM(
CASE WHEN date_time >= date_trunc('month',now()) THEN 1
ELSE 0
END
) AS sales_this_month
,SUM(
CASE WHEN date_time >= date_trunc('month',now()) THEN amount
ELSE 0
END
) AS income_this_month
,SUM(
CASE WHEN date_time >= date_trunc('day',now()) THEN 1
ELSE 0
END
) AS sales_this_day
,SUM(
CASE WHEN date_time >= date_trunc('day',now()) THEN amount
ELSE 0
END
) AS income_this_day
FROM tx
GROUP BY 1
ORDER BY 1 ;


On Oct 28, 12:52 am, crane.j... (AT) gmail (DOT) com wrote:
Quote:
Hi, I'm trying to find the following information from the table found
bellow.

Year_Sales - # of sales that have occurred this year
Year_Income - SUM(amount)
Month_Sales - # of sales that have occurred this month
Month_Income - SUM(amount)
Today_Sales -- # of sales that have occurred today
Today_Icome - SUM(amount)

My table looks like this (simplified):

CREATE TABLE ` Transaction` (
`id` int(10) unsigned NOT NULL auto_increment,
`date_time` datetime NOT NULL,
`user_id` int(10) unsigned NOT NULL,
`amount` int(10) unsigned NOT NULL default '0',
PRIMARY KEY (`id`),
KEY (`date_time `),
KEY `userId` (`userId`),
) ENGINE=InnoDB DEFAULT CHARSET=latin1 |

I'm working on a site that allows people to sell stuff and every time
a seller checks his account he'll see a report showing his
year_sales, year_income, month_sales, etc. Since this query will be
run fairly regularly I'm trying to build this query as efficient as
possible. Also over time the Transaction table will get quite big,
well hopefully J

So far here are the solutions I came up with.

1) Run three queries, (Q1) get year_* info, (Q2) get month_* info,
(Q3) get today_* info. Each query will use where date = .... clauses
to limit the date range accordingly. This feels like a horrible
solution.

2) Use temporary tables

a) Place the results from (Q1) into a temporary table (TQ1), find
year_sales and year_income
b) (Q2) will now query from the temporary table (TQ1) to create a new
temporary table (TQ2), then find month_sales, month_income.
c) (Q3) will now query from the temporary table (TQ2), find
today_sales, today_income.
d) Remove (TQ1), (TQ2)
This solution seems a bit better, but still doesn't feel right.

3) If there is a way to subquery your first

I'm open to suggestions! Thanks in advance

Jake


Reply With Quote
  #3  
Old   
crane.jake@gmail.com
 
Posts: n/a

Default Re: Aggregating Data - Sum(year), Count(year), Sum(month), Count(month), Sum(today), Count(today) - 10-28-2006 , 10:40 PM



Interesting, thanks. I'll play with this a bit. I need to run this
query against a set of products but that should be doable with a join I
suppose.

Thanks a lot!
Jake

shakahshakah (AT) gmail (DOT) com wrote:
Quote:
The syntax may be off as this is from another DB system, but something
along the lines of the following might work for you, or at least give
you some ideas:

SELECT user_id
,SUM(
CASE WHEN date_time >= date_trunc('year',now()) THEN 1
ELSE 0
END
) AS sales_this_year
,SUM(
CASE WHEN date_time >= date_trunc('year',now()) THEN amount
ELSE 0
END
) AS income_this_year
,SUM(
CASE WHEN date_time >= date_trunc('month',now()) THEN 1
ELSE 0
END
) AS sales_this_month
,SUM(
CASE WHEN date_time >= date_trunc('month',now()) THEN amount
ELSE 0
END
) AS income_this_month
,SUM(
CASE WHEN date_time >= date_trunc('day',now()) THEN 1
ELSE 0
END
) AS sales_this_day
,SUM(
CASE WHEN date_time >= date_trunc('day',now()) THEN amount
ELSE 0
END
) AS income_this_day
FROM tx
GROUP BY 1
ORDER BY 1 ;


On Oct 28, 12:52 am, crane.j... (AT) gmail (DOT) com wrote:
Hi, I'm trying to find the following information from the table found
bellow.

Year_Sales - # of sales that have occurred this year
Year_Income - SUM(amount)
Month_Sales - # of sales that have occurred this month
Month_Income - SUM(amount)
Today_Sales -- # of sales that have occurred today
Today_Icome - SUM(amount)

My table looks like this (simplified):

CREATE TABLE ` Transaction` (
`id` int(10) unsigned NOT NULL auto_increment,
`date_time` datetime NOT NULL,
`user_id` int(10) unsigned NOT NULL,
`amount` int(10) unsigned NOT NULL default '0',
PRIMARY KEY (`id`),
KEY (`date_time `),
KEY `userId` (`userId`),
) ENGINE=InnoDB DEFAULT CHARSET=latin1 |

I'm working on a site that allows people to sell stuff and every time
a seller checks his account he'll see a report showing his
year_sales, year_income, month_sales, etc. Since this query will be
run fairly regularly I'm trying to build this query as efficient as
possible. Also over time the Transaction table will get quite big,
well hopefully J

So far here are the solutions I came up with.

1) Run three queries, (Q1) get year_* info, (Q2) get month_* info,
(Q3) get today_* info. Each query will use where date = .... clauses
to limit the date range accordingly. This feels like a horrible
solution.

2) Use temporary tables

a) Place the results from (Q1) into a temporary table (TQ1), find
year_sales and year_income
b) (Q2) will now query from the temporary table (TQ1) to create a new
temporary table (TQ2), then find month_sales, month_income.
c) (Q3) will now query from the temporary table (TQ2), find
today_sales, today_income.
d) Remove (TQ1), (TQ2)
This solution seems a bit better, but still doesn't feel right.

3) If there is a way to subquery your first

I'm open to suggestions! Thanks in advance

Jake


Reply With Quote
  #4  
Old   
Thomas Bartkus
 
Posts: n/a

Default Re: Aggregating Data - Sum(year), Count(year), Sum(month), Count(month), Sum(today), Count(today) - 10-29-2006 , 04:47 PM



On Fri, 27 Oct 2006 21:52:15 -0700, crane.jake wrote:

Quote:
Hi, I'm trying to find the following information from the table found
bellow.

Year_Sales - # of sales that have occurred this year
Year_Income - SUM(amount)
Month_Sales - # of sales that have occurred this month
Month_Income - SUM(amount)
Today_Sales -- # of sales that have occurred today
Today_Icome - SUM(amount)

My table looks like this (simplified):

CREATE TABLE ` Transaction` (
`id` int(10) unsigned NOT NULL auto_increment,
`date_time` datetime NOT NULL,
`user_id` int(10) unsigned NOT NULL,
`amount` int(10) unsigned NOT NULL default '0',
PRIMARY KEY (`id`),
KEY (`date_time `),
KEY `userId` (`userId`),
) ENGINE=InnoDB DEFAULT CHARSET=latin1 |

I'm working on a site that allows people to sell stuff and every time
a seller checks his account he'll see a report showing his
year_sales, year_income, month_sales, etc. Since this query will be
run fairly regularly I'm trying to build this query as efficient as
possible. Also over time the Transaction table will get quite big,
well hopefully J

So far here are the solutions I came up with.

1) Run three queries, (Q1) get year_* info, (Q2) get month_* info,
(Q3) get today_* info. Each query will use where date = .... clauses
to limit the date range accordingly. This feels like a horrible
solution.

2) Use temporary tables

a) Place the results from (Q1) into a temporary table (TQ1), find
year_sales and year_income
b) (Q2) will now query from the temporary table (TQ1) to create a new
temporary table (TQ2), then find month_sales, month_income.
c) (Q3) will now query from the temporary table (TQ2), find
today_sales, today_income.
d) Remove (TQ1), (TQ2)
This solution seems a bit better, but still doesn't feel right.

3) If there is a way to subquery your first

I'm open to suggestions! Thanks in advance
Well - Temporary tables seem feel right to me!
The results of each query are short and sweet and temporary tables are
made for such situations..

Subqueries work fine in later versions of MySQL and you can use them to
wrap everything in one efficient (but ugly!) SELECT query.

However -

Subqueries employ temporary tables behind the scene anyway. So
what's wrong with a series of short, easy to debug, queries
going into temporary tables?

It's what temporary tables are for ;-)
Thomas Bartkus



Reply With Quote
  #5  
Old   
crane.jake@gmail.com
 
Posts: n/a

Default Re: Aggregating Data - Sum(year), Count(year), Sum(month), Count(month), Sum(today), Count(today) - 10-29-2006 , 05:21 PM



Hi Thomas,

Thanks for your feedback.

I was trying really hard to figure out how to do this using sub queries
in one select. I'm using MySQL 5.0.24a so I have access to sub
selects. Are you familiar enough with them that you could show me an
example for this problem?

Maybe a simplified version, say how to find Income_Year and
Income_Month from the table in my original post. I'd be really
interested in seeing how this work. I couldn't seem to figure out how
you use a sub query to select from a result set found in the outer
query.

I agree this would be an ugly query but I would just be interested to
see how it is done. Though I do wonder if letting MySQL handling
creating and removing the temporary tables is more efficient?

Thanks!
Jake


Thomas Bartkus wrote:
Quote:
On Fri, 27 Oct 2006 21:52:15 -0700, crane.jake wrote:

Hi, I'm trying to find the following information from the table found
bellow.

Year_Sales - # of sales that have occurred this year
Year_Income - SUM(amount)
Month_Sales - # of sales that have occurred this month
Month_Income - SUM(amount)
Today_Sales -- # of sales that have occurred today
Today_Icome - SUM(amount)

My table looks like this (simplified):

CREATE TABLE ` Transaction` (
`id` int(10) unsigned NOT NULL auto_increment,
`date_time` datetime NOT NULL,
`user_id` int(10) unsigned NOT NULL,
`amount` int(10) unsigned NOT NULL default '0',
PRIMARY KEY (`id`),
KEY (`date_time `),
KEY `userId` (`userId`),
) ENGINE=InnoDB DEFAULT CHARSET=latin1 |

I'm working on a site that allows people to sell stuff and every time
a seller checks his account he'll see a report showing his
year_sales, year_income, month_sales, etc. Since this query will be
run fairly regularly I'm trying to build this query as efficient as
possible. Also over time the Transaction table will get quite big,
well hopefully J

So far here are the solutions I came up with.

1) Run three queries, (Q1) get year_* info, (Q2) get month_* info,
(Q3) get today_* info. Each query will use where date = .... clauses
to limit the date range accordingly. This feels like a horrible
solution.

2) Use temporary tables

a) Place the results from (Q1) into a temporary table (TQ1), find
year_sales and year_income
b) (Q2) will now query from the temporary table (TQ1) to create a new
temporary table (TQ2), then find month_sales, month_income.
c) (Q3) will now query from the temporary table (TQ2), find
today_sales, today_income.
d) Remove (TQ1), (TQ2)
This solution seems a bit better, but still doesn't feel right.

3) If there is a way to subquery your first

I'm open to suggestions! Thanks in advance

Well - Temporary tables seem feel right to me!
The results of each query are short and sweet and temporary tables are
made for such situations..

Subqueries work fine in later versions of MySQL and you can use them to
wrap everything in one efficient (but ugly!) SELECT query.

However -

Subqueries employ temporary tables behind the scene anyway. So
what's wrong with a series of short, easy to debug, queries
going into temporary tables?

It's what temporary tables are for ;-)
Thomas Bartkus


Reply With Quote
Reply




Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

vB code is On
Smilies are On
[IMG] code is On
HTML code is Off



Powered by vBulletin Version 3.5.3
Copyright ©2000 - 2013, Jelsoft Enterprises Ltd.