How to use subquery to populate column in Access query - sql

I am working on an Access database which is used for forecasting purchases and I am trying to create a query in which would give me list of records with valid prices and row sums.
I am running into problems when I try to combine prices to quantities. I have following tables
Table that contains forecasting data (columns not relevant for this query omitted)
need_rows
ID product_id qty use_date
----------------------------
1 1 100 1.1.2014
2 1 50 15.1.2014
...
And table for prices
prices
ID product_id price valid_from
----------------------------------
1 1 1 1.12.2013
2 1 2 24.12.2013
3 1 5 10.1.2014
...
Query resulst should be something like below:
result of query
product_id use_date qty price sum
---------------------------------------
1 1.1.2014 100 2 200
1 15.1.2014 50 5 250
...
Meaning that I need to fetch valid price to each of the rows based on the use_date from need_rows and valid_from date from prices. Valid prices is the one that has valid_from date equal or most recent to use_date.
Below is one of the approaches I have tried with no luck.
SELECT prices.price
FROM prices
WHERE (((prices.product_id)=[product_id]) AND ((prices.valid_from)=
(SELECT Max(prices.valid_from) AS valid
FROM prices
WHERE (((prices.product_id)=[product_id]) AND ((prices.valid_from)<=[use_date]));).));
Any help is appreciated!

SELECT need_rows.Id
, need_rows.qty
, need_rows.product_id
, (SELECT TOP 1 price
FROM prices
WHERE need_rows.product_id = prices.product_id
AND need_rows.use_date >= prices.valid_from
ORDER BY prices.valid_from DESC) AS currentprice
FROM need_rows;

Related

Multiple select statements - Single result

I have a product list view and a v1 value which is used for mapping
For example in erp view it look like below
PRODUCT_ID
PRODUCT_NAME
QUANTITY
v1
1
WOOD PALLET 120x80
10
25
2
WOOD PALLET 200x80
5
25
25
RAW MATERIAL WOOD
100
25
in postgres we have for it 2 tables
Table: PRODUCTS
PRODUCT_ID
PRODUCT_NAME
QUANTITY
1
WOOD PALLET 120x80
10
2
WOOD PALLET 200x80
5
25
RAW MATERIAL WOOD
100
Table: PRODUCTS_MAPPING
PRODUCT_ID
MAPPING_KEY
1
25
2
25
25
25
Now I need a query that will give only one row result which is total of quantity grouped by v1 so result should be 115
I try below query
(
SELECT
SUM( pr.quantity )
FROM
products AS pr
WHERE
pr.product_id = ( SELECT map.product_id FROM products_mapping AS map WHERE mapping_key = v1 )
)
My problem is that after WHERE there is second SELECT statement which is giving multiple results. I need a statement which will do below calculation:
Check v1 value (25)
Go to product mapping table. Find 3 entry for mapping key 25.
Go to Product table and sum quantity for products_id 1,2,3 and give result 10+5+100 = 115
If I understood properly you only want a single result but you haven't put a group by clause in your sentence.
SELECT sum(pr.quantity) FROM products pr JOIN products_mapping map
on pr.product_id=map.product_id WHERE
mapping_key=v1 group by map.mapping_key
I have rewritten your statement using joins.

How to I stop duplication on SQL join where I have order_ids and when people order more than 1 item (so multiple product_ids) to calculate discounts?

So my problem is my discount number is blowing up because an order has a discount for the entire order, but I am making a dataset where there are multiple lines for each order to represent each product in the order. Instead of the discount only applying once to the order, it adds the discount for every line.
what is happening
order_id
product_id
quantity
amount
discount
1
a
1
5
0
2
a
1
5
7
2
b
1
10
7
3
a
1
5
5
3
b
1
10
5
3
c
1
15
5
what i want
order_id
product_id
quantity
amount
discount
1
a
1
5
0
2
a
1
5
7
2
b
1
10
0
3
a
1
5
5
3
b
1
10
0
3
c
1
15
0
I just want the discount to be applied once per order, and my join is using order_id so that is why the discount is applying multiple times. I would attach my code, but it's a decent sized CTE
Figured it out. I did need to use a row_number() Over Partition by Order id, but I was also losing records if the order had more than 1 item. The solution was to use a CASE WHEN statement.
CASE WHEN ORDER_ROW_COUNT = 1 THEN DISCOUNT ELSE 0 END
this allowed me to keep the records without duplicating the discounts
You’re joining on a field that isn’t unique so the join is returning all the records for that order Id and therefore the discount is being applied to all the records for that order Id. You need some sort of differentiator field. Something that is unique in each orders data set.
Example:
Select *, row_number () over(partition by order_id order by order_id) as rownumber into #temp from table
This should give you something like in the picture.
rownumber table image
Then join on order_Id = order_Id and rownumber =1 and this would only update the first record for each order.

SQL - Counting over several groups

I have a list of transactions where the ID's are repeated and I have the quantity of items being bought. I need to count the number of times that a particular number of items were purchased at once.
Row
ItmNBR
TQTY
1
123
5
2
123
5
3
123
5
3
456
25
4
456
19
I need to produce an out put like this...
ItmNBR
QTY
Occurance
123
5
3
123
19
1
123
25
1
I can get the first two columns of my result but when I attempt to counting over a partition I end up counting getting repeating numbers since I'm only looking up 9 items I just count the number of rows in which the Cnt is the same.
TOT_IVO_ITM_QTY
Count(*) OVER (PARTITION BY QTY) AS CNT
FROM dataset
WHERE YEAR(bus_dt) = 2021
AND ITM_NBR IN (12639,12940,12949,12955,13485,13666,43950,631343,1103731)
AND QTY BETWEEN 5 AND 25
ORDER BY ITM_NBR
,QTY
GROUP BY ITM_NBR, TOT_IVO_ITM_QTY```
I think you just want group by:
select ItmNBR, QTY, count(*)
from t
group by ItmNBR, QTY
order by count(*) desc;
This assumes that you want the count by item and quantity, which seems to be the gist of the question.

Postgres: get average for all values of a column for each distinct from another column

I have a table that looks like:
sku | qty
----|----
sku1| 1
sku1| 3
sku1| 1
sku1| 3
sku2| 1
And I'm trying to write a query that will return the average of qty for each distinct sku.
So for the data above, the output from the query would look like:
sku | qty
----|----
sku1| 2
sku2| 1
So, the averages for sku1 came from 1 3 1 3 and the average of sku2 is just 1
I know it's going to involve some kind of subquery, but I just can't seem to figure it out.
SELECT sku, AVG(qty)
FROM (SELECT DISTINCT sku FROM table)
How do I query for the average qty for each sku?
That's precisely what group by is for:
SELECT sku, AVG(qty)
FROM the_table
GROUP BY sku;
The manual has some examples: http://www.postgresql.org/docs/current/static/queries-table-expressions.html#QUERIES-GROUP

Sum of different column in SQL

We have an existing table with columns:
ItemCode nvarchar
Supplier1Price nvarchar
Supplier2Price nvarchar
Supplier3Price nvarchar
SelectedSupplier int (1, 2 or 3)
The table is used for canvassing from different suppliers. What I want to do is to get the sum of same items from selected suppliers.
Example:
ItemCode Supplier1Price Supplier2Price Supplier3Price SelectedSupplier
item-00 100 200 300 1
item-00 200 100 300 2
item-00 200 100 300 2
item-01 200 300 100 3
item-01 200 100 300 2
Result should be:
ItemCode Total
item-00 300
item-01 200
What I did is this:
select
ItemCode,
sum(SupplierPrice) as Total
from
(select
ItemCode,
case SelectedSupplier
when 1 then Supplier1Price
when 2 then Supplier2Price
when 3 then Supplier3Price
end) as SupplierPrice
from CanvassTable)
group by ItemCode
Note: First, code above selects all itemcodes and corresponding price (from selected supplier). The result then will be processed in order to get the sum of prices of each item.
It's working already, the problem is, I used subquery and I worry that when the table data grows the query will have poor performance. My question is is there any way I can do this without subquery?
If your query works, why not just do:
select
ItemCode,
SUM(case SelectedSupplier
when 1 then Supplier1Price
when 2 then Supplier2Price
when 3 then Supplier3Price
end) as SupplierPrice
from CanvassTable
group by ItemCode