Graphing a single row in an SSRS Line Graph - reporting-services

I have a table setup with the following columns:
Product Name
SalesMonth1
SalesMonth2
SalesMonth3
SalesMonth4
SalesMonth5
An example of a row is as follows:
Bread
300
600
800
900
1000
I am trying to put this into a line graph in SSRS but am having trouble figuring out which fields go where. In my dataset, I have a field for each "SalesMonth" column. So in my dataset, I have 6 fields total including the product name. Will this work? On which axis should the product name go and the sales fields go?

I hope your dataset uses SQL.
I would "unpivot" the data by writing a 5-part UNION SELECT, e.g.
SELECT Product_Name , 1 AS Month , SalesMonth1 AS Sales
UNION ALL
SELECT Product_Name , 2 AS Month , SalesMonth2 AS Sales
UNION ALL
...
SELECT Product_Name , 5 AS Month , SalesMonth5 AS Sales
Then in the SSRS Chart definition:
Month = Category Group
Product Name = Series Group
Sales = Values
But the real real answer is that your data is probably not in a useful shape for reporting. Will there only ever be 5 months? I suspect not...

Related

MySQL Sum and Case Query

I create a ReportViewer with VB.NET connecting to a MySQL database. The data appears like below.
IdProduct Quantity TotalPrice OrderDate
0001 1 10 29/09/2014
0002 2 40 29/09/2014
0001 4 40 29/09/2014
0001 2 20 29/09/2014
0001 2 20 29/09/2014
Based on the records above, I'd like the result to appear like below
0001 0002
9 2
90 40
What is Query Sum Case the best use here? Thanks in advance.
NOTE: It's not possible for a query to "dynamically" alter the number or datatype of the columns returned, those must be specified at the time the SQL text is parsed.
To return the specified resultset with a query, you could do something like this:
SELECT SUM(IF(t.IdProduct='0001',t.Quantity,NULL)) AS `0001`
, SUM(IF(t.IdProduct='0002',t.Quantity,NULL)) AS `0002`
FROM mytable t
UNION ALL
SELECT SUM(IF(t.IdProduct='0001',t.TotalPrice,NULL)) AS `0001`
, SUM(IF(t.IdProduct='0002',t.TotalPrice,NULL)) AS `0002`
FROM mytable t
Note that the datatypes returned by the two queries will need to be compatible. This won't be a problem if Quantity and TotalPrice are both defined as integer.
Also, there's no specific guarantee that the "Quantity" row will be before the "TotalPrice" row; we observe that behavior, and it's unlikely that it will ever be different. But, to have a guarantee, we'd need an ORDER BY clause. So, including an additional discriminator column (a literal in the SELECT list of each query), that would give us something we could ORDER BY.
Note that it's not possible to have this single query dynamically create another column for IdProduct '0003'. We'd need to add that to the SELECT list of each query.
We could do this in two steps, using a query to get the list of distinct IdProduct, and then use that to dynamically create the query we need.
BUT... with all that said... we don't want to do that.
The normative pattern would be to return Quantity and TotalPrice as two separate columns, along with the IdProduct as another column. For example, the result returned by this statement:
SELECT t.IdProduct
, SUM(t.Quantity) AS `Quantity`
, SUM(t.TotalPrice) AS `TotalPrice`
FROM mytable t
GROUP BY t.IdProduct
And then the client application would be responsible for transforming that resultset into the desired display representation.
We don't want to push that job (of transforming the result into a display representation) into the SQL.
select idproduct, sum(quantity), sum(totalprice)
from your_table
group by idproduct

How can I rearrange this table using SAS or MS-Access?

I have a dataset on Microsoft Access and SAS of about a million option prices arranged with the following fields/columns:
DATE, COMPANY, PUT/CALL, PRICE
The PUT/CALL variable is an indicator variable that comes out as either PUT or CALL for each unique DATE-COMPANY combination.
Example with numbers:
DATE COMPANY PUT/CALL PRICE
2001/01/01 XOM PUT 10
2001/01/01 XOM CALL 12
2001/01/01 ABB PUT 11
2001/01/01 ABB CALL 13
What I need is for my table to be arranged with:
DATE, COMPANY, PUT PRICE, CALL PRICE
The above example with numbers, the output should be:
Example with numbers:
DATE COMPANY PUT PRICE CALL PRICE
2001/01/01 XOM 10 12
2001/01/01 ABB 11 13
Would someone know how I could use SAS, Microsoft Access or any other software to complete this?
The following works in Access:
SELECT
[DATE],
[COMPANY],
MAX(IIf([PUT/CALL]="PUT", [PRICE], NULL)) AS [PUT PRICE],
MAX(IIf([PUT/CALL]="CALL", [PRICE], NULL)) AS [CALL PRICE]
FROM [PRICES]
GROUP BY [DATE], [COMPANY];
Note that...
several of the column names have spaces or "funny characters" in them, and
DATE is a reserved word in Access,
...so the square brackets [] are important.
In SAS this is pretty easy.
Assuming your first table is a dataset named 'HAVE', and is sorted by date/company:
proc transpose data=have out=want suffix=price;
by date company;
id put_call;
var price;
run;
In Access (or SQL) you'd want to do a SQL query, something like this:
create table want as select date,company,
max(case when put_call='put' then price else null end) as put_price,
max(case when put_call='call' then price else null end) as call_price
from have group by date,company;
In SQL server you could probably do this with a pivot.

Query to get the output as shown in designation table

EmpId EmpDeptName
1 Account
2 Sales
3 IT
4 HR
i want output in the format
EmpId Account Sales IT HR
1
2
3
4
If anybody knows how to write query to get this output , please provide me that query.
This type od data transformation is a PIVOT, where you take row data and convert it to columns.
You did not provide many details, but if you wanted the count of employees in each department, you could use something like this:
select Account, Sales, IT, HR
from
(
select EmpDeptName
from employees
) d
pivot
(
count(EmpDeptName)
for EmpDeptName in (Account, Sales, IT, HR)
) p;
This will display the total number of employees in each department as column data instead of rows.

N or more continuous year range

I have to create a report using MySql DB where more than 4 tables are involved. I have one table (S1) with S1_ID and S1_Year_Range (strings like 2001-2002) and another table (S2) with S2_ID(PK), S2_Customer_ID, S1_ID (FK) and other fields for other conditions that can appear in Where clause of my query. There can be more than one row in S2 with the same S2_Customer_ID but different S1_ID. My query is to create a report using VB.net and ask users to enter two values; one number for how many continuous years or bigger (like >= 5 years), and a year range value (like 2011-2012) which is the highest value in the list for all customers.
My report lists customer names (by joining the above query with another table), customer rank and all year range values (highest at the bottom) for that customer in one column for each customer. Any help for this query would be appreciated.
Data and results could be like the following:
S1:
(S1_ID....S1_Year_Range)
(1......2000-2001)
(2......2001-2002)
(3......2002-2003)
(4......2003-2004)
(5......2004-2005)
etc
S2:
(S2_ID.....S2_Customer_ID.....S1_ID)
(1....1....1)
(2....1....2)
(3....1....3)
(4....2....2)
(5....2....3)
(6....2....5)
(7....3....2)
(8....3....3)
(9....3....4)
(10...3....5)
(11...4....3)
(12...4....4)
(13...4....5)
etc
when number 2 and year range (2003-2004) is entered by the user, the result should be the following:
customer 3 with 3 year range values (2003-2004, 2002-2003, and 2001-2002) and customer 4 with 2 year range values (2003-2004 and 2002-2003):
cname3
2001-2002
2002-2003
2003-2004
cname4
2002-2003
2003-2004
I hope you can see the columns of the report correctly.
I finally created a complex query to solve my problem. In the following query, I encoded the user year range value as '2010-2011' and number of continuous years as 14. Also a tiny difference with the question is the table names; table CSP here is the same as table S2 in my question but field names are the same as those in my question.
SELECT CSYWFY.S2_Customer_ID, COUNT(CSYWFY.S2_Customer_ID)
FROM (SELECT S1F.S1_Year_Range, S2.S2_Customer_ID , COUNT(S1F.S1_Year_Range) FROM CSP as S2 INNER JOIN S1 as S1F ON S2.S1_ID = S1F.S1_ID WHERE '2010-2011' IN (SELECT S1N.S1_Year_Range FROM CSP as S2N INNER JOIN S1 as S1N ON S2N.S1_ID = S1N.S1_ID WHERE S2N.S2_Customer_ID = S2.S2_Customer_ID ) GROUP BY S2.S2_Customer_ID ASC , S1F.S1_Year_Range DESC ) CSYWFY
GROUP BY CSYWFY.S2_Customer_ID
HAVING COUNT(CSYWFY.S2_Customer_ID) > 14
HTH

How would I do this in MySQL?

Lets say I have a database of widgets. I am showing a list of the top ten groupings of each widget, separated by category.
So lets say I want to show a list of all widgets in category A, but I want to sort them based on the total number of widgets in that category and only show the top 10 groupings.
So, my list might look something like this.
Top groupings in Category A
100 Widgets made by company 1 in 1990.
90 Widgets made by company 1 in 1993.
70 Widgets made by company 3 in 1993.
etc...(for 10 groupings)
This part is easy, but now lets say I want a certain grouping to ALWAYS show up in the listings even if it doesnt actually make the top ten.
Lets say I ALWAYS want to show the number of Widgets made by company 1 in 2009, but I want this grouping to be shown somewhere in my list randomly (not first or last)
So the end list should look something like
Top groupings in Category A
100 Widgets made by company 1 in 1990.
90 Widgets made by company 1 in 1993.
30 Widgets made by company 1 in 2009.
70 Widgets made by company 3 in 1993.
How would i accomplish this in MySQL?
thanks
Edit:
Currently, my query looks like this
SELECT
year,
manufacturer,
MAX(price) AS price,
image_url,
COUNT(id) AS total
FROM
widgets
WHERE
category_id = A
AND
year <> ''
AND
manufacturer <> ''
GROUP BY
category_id,
manufacturer,
year
ORDER BY
total DESC,
price ASC
LIMIT
10
);
Thats without the mandatory grouping in there.
The placement doesnt necessarily have to be random, just shouldnt be on any extreme end. And the list should be 10 groupings including the mandatory listing. So 9 + 1
I would use an UNION query: your current query union the query for 2009, then handle the sorting in the presentation layer.
You can write 2 separate query (one for all companies and another just for company 1) and then use UNION to join them together. Finally, add ORDER BY RAND().
It will look like
SELECT * FROM
(
SELECT company_id, company_name, year, count(*) as num_widgets
....
LIMIT 10
UNION DISTINCT
SELECT company_id, company_name, year, count(*) as num_widgets
...
WHERE company_id =1
...
LIMIT 10
)x
ORDER BY RAND();
You could add a field that you make true for company 1 in 2009 and include it in the where clause. Something like
select * from companies where group = 'some group' or included = true order by included, widgets_made limit 10
For the random part you would have that as subquery then include a column that has a random number from 1 to 10 if the field that you made is true, and rownum otherwise, then sort by that column