sql 3 tables sum - sql

I have 3 tables, bookings, companies and flights. bookings has no_seats andseat_price. I need to calculate sum of no_seats * seat_price for each company (for all their flights together). flight has company_id and booking has flight_id. What's the best way to do that?

Assuming "companies" has a 1-to-many relation with "flights" and "flights" have 1-to-many relation with "bookings":
select c.CompanyName, sum(b.no_seats * b.seat_price) as total
from Companies c
inner join Flights f on f.Company_Id = c.Company_id
inner join Bookings b on b.Flight_ID = f.Flight_ID
group by c.Company_ID, c.CompanyName;

Your question doesn't provide enough informations, but I guess this is what you want ?
Select C.Company_Id, SUM( B.no_seats * B.seat_price) as [Desired Calculation]
From Company C, Flights F, Bookings B
Where C.Company_Id = F.Company_Id
And F.Flight_Id = B.Flight_Id
Group By C.Company_Id
If there are any further questions please feel free to ask.

Related

How to make this query on PostgreSQL?

I have three tables:
Customer table
Product Table
Customer_Product Table
I need to make query: Search for customers who bought a certain product (for example, name = "toilet paper") at least 2 times
I don't understand how.. I'm noob in databases.. Please help
You need aggregation :
select c.name
from customer c inner join
customer_product cp
on cp.customer_id = c.customer_id inner join
product p
on p.product_id = cp.product_id
where p.lable = 'toilet paper'
group by c.name
having count(p.lable) > 1;

How to get count of customers?

I need some help with an SQL query.
Let's say we have this sample database which manages Bookings in a hotel:
Customer(ID, name, birthDate, city);
Room(number, floor, beds, roomtype, price);
Bookings(Customer, roomNumber, floor, checkInDate, checkOutDate);
I need to know which customers booked only and ONLY economic type of rooms.
This is my query:
select Customer from Bookings
join Room on(Bookings.num = camera.roomNumber and Bookings.floor=
Room.floor)
where (Bookings.Customer, Bookings.floor) not in (select number, floor from
Room where roomType != 'economic')
My issue is that this query shows me customers which booked economic rooms, but it also shows me customers which booked other type of rooms.
How can I restrict the output in order to get Customers which booked ONLY economic rooms?
Thank you
Use not exists :
select c.*
from Customer c
where not exists (select 1
from Bookings b
inner join Room r on b.num = r.roomNumber and b.floor = r.floor
where c.ID = b.Customer and r.roomType <> 'economic'
);
You can use aggregation:
select b.Customer
from Bookings b join
Room r
on b.num = r.roomNumber and b.floor = r.floor
group by b.Customer
having min(roomType) = max(roomType) and min(roomType) = 'economic';

SQL Query for all students who purchased a book that is cited by a book that is higher price

So i have a student table with name and sid, which relates to sid in table buys. Buys also has a bookno field which relates to bookno in table cites (citations). Cites has a citedbookno field that relates to bookno in the table book.
Right now i only have all students who have purchased a book, but would like to refine it to show only those students who have bought a book that is cited by at least one book with a higher price. Im not sure exactly how to write the count query here. Any help would be appreciated. Thanks!
SELECT DISTINCT s.sid, s.sname
FROM student s
WHERE s.sid IN (SELECT r.sid
FROM buys r
WHERE b.bookno IN (SELECT c.bookno
FROM cites c
WHERE c.citedbookno IN (SELECT b.bookno
FROM book b
WHERE b.bookno = c.citedbookno)));
Simple version:
select distinct student.sid, student.sname
from student
inner join
buys
on buys.sid = student.sid
inner join
book
on book.bookno = buys.bookno
inner join
cites
on cites.citedbookno = book.bookno
inner join
book bookExpensive
on bookExpensive.bookno = cites.bookno
where bookExpensive.price > book.price
This is the same, but might perform better:
select student.sid, student.sname
from student
where exists(
select 1
from buys
inner join
book
on book.bookno = buys.bookno
where buys.sid = student.sid
and
exists(
select 1
from cites
inner join
book bookExpensive
on bookExpensive.bookno = cites.bookno
where cites.citedbookno = book.bookno
and
bookExpensive.price > book.price
)
)
Assuming cites.citedbookno is the bookno of a book being cited.
SELECT
s.sid,
s.sname
FROM Student s
WHERE s.sid IN (
SELECT r.sid
FROM buys r
JOIN cites c ON r.bookno = c.citedbookno
);

Display 2 columns from one table having max count in column 3 and display computed sum of values from another table

I've a customer table and purchases table,
need to show cname, cid with max(customer_visits) from customer table
and sum of total_purchases by customer in purchases table.
I'm doing something like this
select p.cid, c.cname, sum(p.total_price)
from customers c where exists
(select max(visits_made) from customers having visits_made=max(visits_made)
and cid=p.cid)
inner join purchases p on p.cid=c.cid
group by p.cid,c.cname
and
select p.cid, c.cname, sum(p.total_price)
(select max(visits_made) from customers c where c.cid=p.cid)
from purchases p
inner join customers c on c.cid=p.cid
group by p.cid,c.cname
What's going wrong with these queries?
Found the solution, had to include where clause after inner join :D
I think this is just an aggregation query:
select p.cid, c.cname, sum(p.total_price) as total_price,
max(visits_made) as visits_made
from purchases p inner join
customers c
on c.cid = p.cid
group by p.cid, c.cname;

Issues with joining many tables getting to many values

This is my script:
select c.rendering_id as prov_number, c.begin_date_of_service as date_of_service,
c.practice_id as group_number, v.enc_nbr as invoice, p.person_nbr as patient,
v.enc_nbr as invoice_number, c.charge_id as transaction_number,
t.med_rec_nbr as primary_mrn, p.last_name, p.first_name,
z.payer_id as orig_fsc_number, z.payer_id as curr_fsc_number,
c.location_id as location_number, c.closing_date as posting_date,
c.quantity as service_units, c.amt as charge_amount,
c.cpt4_code_id as procedure_code, r.description as procedure_name,
x.tran_code_id as pay_code_number, ISNULL([modifier_1],'') as modifier_code_1,
ISNULL([modifier_2],'') as modifier_code_2, ISNULL([modifier_3],'') as modifier_code_3,
ISNULL ([icd9cm_code_id],'') as dx_code_1, ISNULL ([icd9cm_code_id_2],'') as dx_code_2,
ISNULL ([icd9cm_code_id_3],'') as dx_code_3, ISNULL ([icd9cm_code_id_4],'') as dx_code_4
from charges c, person p, patient t, patient_encounter v, encounter_payer z, cpt4_code_mstr r, transactions x
where c.person_id = p.person_id
and c.person_id = t.person_id
and c.person_id = v.person_id
and c.person_id = z.person_id
and c.cpt4_code_id = r.cpt4_code_id
and c.person_id = x.person_id
and c.practice_id = '0001'
and c.closing_date >= GetDate() - 7
I should be getting about 14k rows but with this I am getting a couple hundred thousand. I feel like there should be an inner join here to correct it but I have read through a bunch of posts and can seem to get it working. Its by far the biggest pull I have ever done in SQL.
Any help would be greatly help.
Without knowing more about the data structures and foreign key relationships, this answer is just educated speculation. Before answering, though, you need to learn proper JOIN syntax. Your query should look like:
from charges c join
person p
on . . . .
That said, you problem is probably that you are joining along multiple dimensions at the same time. Although not explicitly clear, I am guessing that a person could have multiple patient encounters, say A, B, and C. A person might also have multiple charges, say 10, 11, and 12.
Your query will produce nine rows in this case, one for each combination.
In other words, you need to identify:
Verify the join keys between tables. Is a table called transactions really joined to encounters and costs using the person_id?
Find out where you are getting cross products, and split into two subqueries that are then appropriately joined together.
I would suggest that you start with the first two tables, and see whether you get the expected row count for:
select *
from charges c join
person p
on c.person_id = p.person_id
where c.practice_id = '0001' and
c.closing_date >= GetDate() - 7
Then build up the query one table at a time to get the results you want.
One last note, when using table aliases, I find it much clearer to use aliases that evoke the table. "C" for charges is very good. Consider something like "pe" for patient_encounters, and so on.
It should be like this or you can use left join
select c.rendering_id as prov_number, c.begin_date_of_service as date_of_service,
c.practice_id as group_number, v.enc_nbr as invoice, p.person_nbr as patient,
v.enc_nbr as invoice_number, c.charge_id as transaction_number,
t.med_rec_nbr as primary_mrn, p.last_name, p.first_name,
z.payer_id as orig_fsc_number, z.payer_id as curr_fsc_number,
c.location_id as location_number, c.closing_date as posting_date,
c.quantity as service_units, c.amt as charge_amount,
c.cpt4_code_id as procedure_code, r.description as procedure_name,
x.tran_code_id as pay_code_number, ISNULL([modifier_1],'') as modifier_code_1,
ISNULL([modifier_2],'') as modifier_code_2, ISNULL([modifier_3],'') as modifier_code_3,
ISNULL ([icd9cm_code_id],'') as dx_code_1, ISNULL ([icd9cm_code_id_2],'') as dx_code_2,
ISNULL ([icd9cm_code_id_3],'') as dx_code_3, ISNULL ([icd9cm_code_id_4],'') as dx_code_4
from charges c
inner join person p on c.person_id = p.person_id
inner join patient t on c.person_id = t.person_id
inner join patient_encounter v on c.person_id = v.person_id
inner join encounter_payer z on c.person_id = z.person_id
inner join cpt4_code_mstr r on c.cpt4_code_id = r.cpt4_code_id
inner join transactions x on c.person_id = x.person_id
where c.practice_id = '0001'
and c.closing_date >= GetDate() - 7
Now you comment one inner join at a time and execute below query and see which of these joins is causing one to many relationship...when the count gives you say around 14 K that means the commented table is causing 1 to many relationship.
Otherwise best way is to find the relationship based on unique key,primary key and FK on these tables.
select
count(c.person_id)
from charges c
inner join person p on c.person_id = p.person_id
inner join patient t on c.person_id = t.person_id
inner join patient_encounter v on c.person_id = v.person_id
inner join encounter_payer z on c.person_id = z.person_id
inner join cpt4_code_mstr r on c.cpt4_code_id = r.cpt4_code_id
inner join transactions x on c.person_id = x.person_id
where c.practice_id = '0001'
and c.closing_date >= GetDate() - 7
You can try
select count(*) from <tablename> group by person_id having count(*) > 1
and repeat above query for all tables this will give you an idea on what kind of relationship between charges table and other tables. Offcourse use cpt4_code_id for cpt4_code_mstr table but by name it looks like that this table is master table so it will have a signle vale for each cpt4-code_id value in charges table.
I hope it will help