how to work with Derived Tables - sql

I am trying to understand a derived tables I kinda have an idea but still messing with it. I did this code that I dont think is right. I don't know if I have something input wrong or left something out. The table I am working with is a distinct company name from the customers table where the orders have a higher discount than.2.I have been looking over it maybe I have some of the names backwards or something.
SELECT DISTINCT c.CompanyName
From Customers As c
Join
(Select OrderID
From Orders as o
Join [Order Details] as od
ON c.Customers = od.OrderID
Where od.OrderID = '<.2'
The last Part is not working so well with the.2
How the columns are set up in the northwind database you click on tables and go down to see the dbo.Order Details and click on columns you will find OrderId, ProductID, UnitPrice, Quantity, Disounts. Then you will have the Custumers table which had CustomerID, CompanyName, ContactName, ContactTitle, Address, City, Region, PostalCode, COuntry, Phone, and Fax. Now if you go under the order table you will have OrderID, CustomerID, EmployeeID, OrderDate, RequiredDate, ShippedDate,ShipVia, Frieght, ShipName, ShipAddress, ShipCity, ShipRegion, ShipPostalCode, ShipCountry.

Something like this should do it.
SELECT c.CompanyName
FROM Customers c
WHERE EXISTS(SELECT NULL
FROM Orders o
INNER JOIN [Order Details] od
ON o.OrderID = od.OrderID
AND od.Discount > .2
WHERE o.CustomerID = c.CustomerID)

Related

How do you add OrderID to this? I cant get it to display without getting a error on all OrderID sections

I cant get it to display without getting an error on all OrderID sections. I tried adding it to the top and then the subquery and it errors saying ambouious column. How would be the correct way to do this?
TABLE SETUP:
Customers Table:
CustomerID, EmailAddress, Password, FirstName, LastName, ShippingAddressID, BillingAddressID
OrderItems Table:
ItemID, OrderID, ProductID, ItemPrice, DiscountAmount, DiscountTotal, PriceTotal, ItemTotal, Quantity
Order Table:
OrderID, CustomerID, OrderDate, ShipAmount, TaxAmount, ShipDate, ShipAddressID, CardType, CardNumber,CardExpires, BillingAddressID
CODE:
SELECT c.EmailAddress, MAX(OrderCost) AS
LargestOrder
FROM Customers c
JOIN ORDERS o ON c.CustomerID = o.CustomerID
JOIN (Select Orders.OrderID, ItemPrice * Quanity AS OrderCost FROM Orders, OrderItems
WHERE OrderItems.OrderID = Orders.OrderID)Largest
ON Largest.OrderID = o.OrderID
GROUP BY c.EmailAddresses
It really helps for you to put some effort into a script that demonstrates your problem. That way no one needs to guess about how you defined things and the actual values you use.
Here is one approach based on my guess. Note "one" - there are techniques to achieve the same result. The cte calculates the total cost for each order just like your code attempted. Since you suggested top, I used that as well to demonstrate its usage. Grabbing the top first row based on descending OrderCost will get you the order with the highest total cost. Just join the cte to Orders and Customers to include the columns you desire.
with cte as (select OrderID, sum(ItemPrice * Quantity) as OrderCost
from #OrderItems
group by OrderID)
select top 1 Ord.OrderID, Ord.OrderDate, cust.EmailAddress, cte.OrderCost
from cte inner join #Orders as Ord
on cte.OrderID = Ord.OrderID
inner join #Customers as Cust
on Ord.CustomerID = Cust.CustomerID
order by cte.OrderCost desc;
rextester here
And everyone hopes that you are not actually saving credit card information - because that would be bad in many ways.

Access Query from multiple tables

I currently have an Access Database with a few tables, among them Order, OrderDetails and Client.
Order (OrderID, TimeStamp, FKEmployeeID, FKClientID, OrderStatus, Comments)
OrderDetails (OrderDetailsID, FKOrderID, FKProductID, Quantity, Cost, Total Cost)
Client (ClientID, Name)
I'm trying to build a query where I can get the total orders that a client has made and the total Items.
Example:
Customer, Total Orders, Total Items
John, 5, 15
Alex, 2, 30
Ana, 1, 3
Whenever I try to make a query Total Orders and Total Items give me the same number.
Any help would be greatly appreciated!
This is supported even by ms access:
SELECT c.Name,
(select count(*)
from Orders o
where o. FKClientID = C.ClientID) as [Total Orders],
(select sum(Quantity) as Items
from OrderDetails od
inner join Order o on o.OrderID = od.FKOrderID
where o.FKClientId = C.ClientID) as [Total Items]
from Client c;
Unfortunately, MS Access doesn't support COUNT(DISTINCT). You can do this with two aggregations:
SELECT c.[Name], COUNT(*) As NumOrders, SUM(o.NumItems) As NumItems
FROM Client as c INNER JOIN
(SELECT o.OrderID, o.FKClientID, COUNT(*) As NumItems
FROM [Order] as o INNER JOIN
OrderDetails as od
ON od.FKOrderID = o.OrderID
GROUP BY o.OrderID, o.FKClientID
) as o
ON o.FKClientID = c.ClientId
GROUP BY c.ClientId, c.Name;
What about this solution (clients without orders are left out hereby):
SELECT Client.[Name],
Count(myTotalItems.OrderID) As TotalOrders,
Sum(myTotalItems.TotalItems) As TotalItems
FROM Client,
(SELECT First([Order].OrderID) As OrderID,
First([Order].FKClientID) As
ClientID,
Count(OrderDetails.OrderDetailsID) As TotalItems
FROM [Order], OrderDetails
WHERE OrderDetails.FKOrderID like [Order].OrderID
GROUP BY [Order].OrderID) As myTotalItems
WHERE myTotalItems.ClientID like Client.ClientID
GROUP BY Client.[Name];
It would be easier for you if you divide the task into multiple queries. I am giving the sample using Northwind database, you can test and see on it. Note that the structures and fieldnames are very similar to yours.
First create one that gets ClientId, OrderId, OrderDate and Sum of Quantity.
SELECT c.CustomerId, o.OrderId, o.OrderDate, sum(od.Quantity) AS Qty
FROM (Customers AS c INNER JOIN Orders AS o ON c.CustomerId = o.CustomerId)
INNER JOIN [Order Details] AS od ON o.OrderId = od.OrderID
GROUP BY c.CustomerId, o.OrderId, o.OrderDate;
Save this as "OrderOfClients" (it would be saved in Queries). Next create a query that uses this one and asks for date range:
SELECT c.CustomerId, c.CompanyName,
Count(*) AS [Total Orders],
Sum(Qty) AS [Total Items]
FROM Customers AS c
INNER JOIN OrdersOfClients AS co ON c.CustomerId = co.CustomerId
WHERE co.OrderDate Between [#startDate] And [#endDate]
GROUP BY c.CustomerId, c.CompanyName;
You can save this one as "OrdersOfClientsSummary" and call for your report.
PS: In my personal opinion, if you use a database other than access you would be doing yourself a big favor.

Does this SQL statement require a nested SELECT query?

Here is what I have so far but the results are wrong.
SELECT c.CompanyName,
COUNT(o.OrderID) AS [Total Orders],
SUM(
(od.UnitPrice -
(od.UnitPrice * od.Discount))* Quantity) AS [Purchase Total]
FROM Customers AS c,
Orders AS o,
[Order Details] AS od
WHERE c.CustomerID = o.CustomerID
AND o.OrderID = od.OrderID
GROUP BY c.CompanyName
ORDER BY c.CompanyName;
The issue I am having is with the count, it is off by double or more. I believe that this is because the OrderID appears multiple times in the Order Details table. I think I need a nested SELECT statement but I am unsure how to do that.
Would I be removing the SUM() expression, Order Details, and the AND clause from the first query? Or am I way off?
With help I have gotten the COUNT field to work but now my SUM field is wrong. This is my most recent attempt and it produces the same value for every customer.
SELECT c.CompanyName,
COUNT(o.OrderID) AS [Total Orders],
(SELECT SUM(
(odIN.UnitPrice -
(odIN.UnitPrice * odIN.Discount)) * odIN.Quantity) AS [OrderTotal]
FROM [Order Details] AS odIN, Orders As oIN
WHERE odIN.OrderID = oIN.OrderID) AS [Purchase Total]
FROM
Customers AS c, Orders AS o
WHERE c.CustomerID = o.CustomerID
GROUP BY c.CompanyName
ORDER BY c.CompanyName;
I was unsuccessful at getting the query to fully work the way I wanted it to. Then I realized that maybe maybe I was looking for the wrong data. So I switched the name for the COUNT field to Num Products Purchased.
I would still like to get the other way working, but I think that will require creating a temporary table or view that could be used to do one of the calculations and then call it from the query. That is something I'll have to figure out.
Thank you for the attempts to help.
Because Access doesn't have COUNT(DISTINCT) then you need to create an inner query.
What this does is compute the sum of each item in an order in the inner query, and then sums up all the order totals for the customer as the purchase total. An individual OrderID will not be counted twice, as o and od now have a one to one relationship.
There might be a syntax error in there somewhere, but the idea should work.
SELECT c.CompanyName,
COUNT(o.OrderID) AS [Total Orders],
SUM(od.OrderTotal) AS [Purchase Total]
FROM
Customers AS c,
Orders AS o,
(SELECT odIn.OrderID,
SUM(
(odIn.UnitPrice -
(odIn.UnitPrice * odIn.Discount)) * odIn.Quantity) AS [OrderTotal]
FROM [Order Details] AS odIn
GROUP BY odIn.OrderID) AS od
WHERE c.CustomerID = o.CustomerID
AND o.OrderID = od.OrderID
GROUP BY c.CompanyName
ORDER BY c.CompanyName;
if the problem is because OrderID appears multiple times, try:
SELECT c.CompanyName, COUNT(DISTINCT o.OrderID) AS [Total Orders], SUM((od.UnitPrice - (od.UnitPrice * od.Discount)) * Quantity) AS [Purchase Total]
FROM Customers AS c, Orders AS o, [Order Details] AS od
WHERE c.CustomerID = o.CustomerID AND o.OrderID = od.OrderID
GROUP BY c.CompanyName
ORDER BY c.CompanyName;
The distinct clause lets you count only each appearance.
First I would like to thank Daniel for his help. I did finally get the query to work with help from another source. Daniel's solution is better as it requires less code and even formats the sum in currency.
Here is the one I got to work:
SELECT vtOrdCnt.*, ROUND(vtTotCost.PurchaseTotal, 2) AS [Purchase Total]
FROM
(
SELECT CustomerID, COUNT(OrderID) AS TotalOrders
FROM orders
GROUP BY CustomerID
) AS vtOrdCnt,
(
SELECT CustomerID, SUM(UnitPrice * (1-Discount)*Quantity) AS PurchaseTotal
FROM Orders AS o, [Order Details] AS od
WHERE o.orderID = od.orderID
GROUP BY CustomerID
) AS vtTotCost
WHERE vtOrdCnt.CustomerID = vtTotCost.CustomerID
ORDER BY vtOrdCnt.CustomerId
By using Aliases and two select statements in the FROM clause it allowed the query to function the way I wanted it to.

SQL Server query for total dollar amount of orders per customerID

I have two tables that I need to create a query for. I'm sure I'll need to join them as well.
I need to take the CustomerName and Address of customer from my Customer table but I also need the query to show the total dollar amount of all the orders placed by customer. So if the customer spent for example $300 dollars this year in total, that $300 is the output I'm trying to achieve.
I have a table called Order Details that uses an OrderID which is tied to a CustomerID and there are unitprice and quantity columns in the Order Details table. I'm trying to figure out how to multiple these but I am going crazy.
I have tried this to get at least the total from the orders but I have syntax errors for sure:
SELECT unitprice,
quantity
FROM [Order details] (unitprice * quantity) AS Totalorders,
from [Order Details]
WHERE orderid > 0
also this without any luck :
SELECT customers.companyname AS 'Company Name',
customers.address AS 'Address',
[order details].unitprice * [order details].quantity AS 'Orders'
FROM customers
LEFT JOIN orders
ON customers.customerid = orders.customerid
ORDER BY customers.companyname,
customers.address,
orders
Thanks
You need to join in the order details and do a group by aggregation:
SELECT c.CompanyName AS "Company Name",
c.Address AS "Address",
sum(od.Unitprice * od.quantity) as "Orders"
FROM Customers c LEFT JOIN
Orders o
ON c.CustomerID = o.CustomerID left join
[Order Details] od
on od.orderid = o.orderid
GROUP BY c.CompanyName, c.Address
ORDER BY c.CompanyName, c.Address
In addition, I made some stylistic changes. I added aliases to the table names. I find it much easier to read c.CompanyName rather than Customers.CompanyName. I changed the delimiter on the column aliases to use double quotes rather than single quotes. I associate single quotes with string constants inside the statement.
if it s one-to-many relationship, your query will look something like:
SELECT
Customers.CompanyName AS 'Company Name',
Customers.Address AS 'Address',
SUM(O.Unitprice * O.quantity) as 'Orders'
FROM Customers
LEFT JOIN [Order Details] O
ON Customers.CustomerID = O.CustomerID
GROUP BY Customers.CompanyName, Customers.Address
ORDER BY Customers.CompanyName, Customers.Address

How to use Max function on another column from a select

There is query which is asking for favourite products which is bought by each coustomer. i have to select and in the first select i have selected the count of products that each customer bought. in the other select i want to select the maximum of that boughts for each customer.but when i want to select max(previous select column) it gets and error and says it is not defined can any one helps me how to fix this problem. i am very motivated to solve the problem from this way, and i am not willing to use other methods like creating view or something like that. can any one help me on this:
SELECT INN.Maximum,INN.Name, customer.ProductName from
(SELECT ContactName, ProductName, COUNT([Order Details].Quantity) AS NumOftimeCustomer
FROM Orders, [Order Details], Products, Customers
WHERE [Order Details].OrderID = Orders.OrderID
AND [Order Details].ProductID = Products.ProductID
AND Orders.CustomerID = Customers.CustomerID
GROUP BY ContactName, ProductName)customer
INNER JOIN
(SELECT Customers.ContactName AS Name, **MAX(customer.numOftimecustomer)** AS Maximum
from Customers, customer
GROUP BY Customers.ContactName) INN
ON INN.Name = customer.ContactName AND INN.Maximum = customer.NumOftimeCustomer
that part which is mentioned with MAX(customer.numOftimecustomer) ** is the part which gives error and it says the object customer is not defined. is there a way to solve it without view? why is it in this way? since the customer that i defined is not a table?
here is what you want:
select
*
from (SELECT ContactName, ProductName, COUNT([Order Details].Quantity) AS NumOftimeCustomer
FROM Orders, [Order Details], Products, Customers
WHERE [Order Details].OrderID = Orders.OrderID
AND [Order Details].ProductID = Products.ProductID
AND Orders.CustomerID = Customers.CustomerID
GROUP BY ContactName, ProductName)customer
where customer.num = (select max(num) from
(SELECT ContactName, ProductName, COUNT([Order Details].Quantity) AS NumOftimeCustomer
FROM Orders, [Order Details], Products, Customers
WHERE [Order Details].OrderID = Orders.OrderID
AND [Order Details].ProductID = Products.ProductID
AND Orders.CustomerID = Customers.CustomerID
GROUP BY ContactName, ProductName)customer2
where customer2.name = customer.name)