SQL programming - sql

how can I determine the number of CoE students per school per city?
the coe students belongs to a different table from the school table from the city table. I really need some help now. thanks

I assume that there is a relation between the school and the student tables, and one between the school and the city tables, as that it that makes sense.
Join the tables together, group on the school and the city, and count the students. Something like:
select sc.Name, c.Name, count(*) as students
from Student st
inner join School sc on sc.Id = st.SchoolId
inner join City c on c.Id = sc.CityId
group by sc.Name, c.Name

You'll need to use a JOIN to link the tables, GROUP BY on School and city and COUNT Without further details of your table structure I can't give you a specific query to use!

Go step by step: start listing all the students. Then try listing all the students and their school, by finding what is the relationship between the student table and the school table. Then try listing all students with their school and city.
Once you've worked out how to join these tables, you can search how to aggregate the results to get the required output.

Related

Getting data for each Student from other tables

I am trying to get information for each student in a database. I know that there are exactly 4 students and that between all students, there are 6 enrollments (ie. some students are enrolled in multiple courses). Therefore, the proper output would have 6 rows, all containing the necessary student info. There would be duplicate students in the returned query. I am able to join the students and the enrollments just fine and end up with the 6 total enrollments. However, once I join in the other tables to get data about the courses that the students are enrolled in, I end up getting more and more rows. Depending on how I format my query, I get between 7-11 rows. All that I want is the 6 rows that correspond to the enrollments and nothing more. Why does that happen like this and how do I fix it?
I have tried different kinds of joins, unions, intersections, and have been working at the question for well over an hour. This is what I have currently:
Select s.sid, e.term, c.cno, e.secno, ca.ctitle
from Students as s
join Enrolls as e
on s.sid = e.sid
join Courses as c
on e.secno = c.secno
join Catalogue as ca
on ca.cno = c.cno
question details
database details
It looks like the Courses and Enrollment tables have what we call 'a composite key'. I bet you must join the c and e tables with both term and secno columns.
Your query mus be like this:
SELECT s.sid, e.term, c.cno, e.secno, ca.ctitle
FROM Students AS s
JOIN Enrolls AS e ON s.sid = e.sid
JOIN Courses AS c ON e.secno = c.secno AND e.term = c.term
JOIN Catalogue AS ca ON ca.cno = c.cno
When you have a composite key and uses only one of the columns to join, you will get unwanted rows from the foreign table, making a Cartesian product result

Finding out zero frequency values from a column with inner join

I have two tables named courses and teachers. I need to find the list of teachers who don't take any courses.
This is the query I wrote for getting the teacher who took the most numbered courses -
SELECT t.name AS teacher_name
, COUNT(c.teacher_id) AS courses_taken
FROM courses c
JOIN teachers t
ON c.teacher_id = t.id
GROUP
BY c.teacher_id
ORDER
BY courses_taken DESC
LIMIT 1;
By reversing this query I am getting the teacher's list who take minimum numbers of courses which is 1 but I need to find the list of teacher who don't take any courses.
Left Join and Where condition can help you.
SELECT *
FROM teachers t
LEFT
JOIN courses c
ON t.id = c.teacher_id
WHERE c.teacher_id IS NULL
Teachers don't usually "take" courses. They "teach" courses. Students "take" courses.
That said, not exists seems appropriate:
SELECT t.*
FROM teachers t
WHERE NOT EXISTS (SELECT 1
FROM courses c
WHERE c.teacher_id = t.id
);
If you think about this, it is almost a direct translation of your question: Get teachers where there is no course that the teacher teachers.

SQL select multiple rows and order them by id

I got a Student with a few parameters, like Id, Name, etc.
Now I got another one table called ACCOUNTS, they have an id and a name...
the relation between these two is OneToMany (one student can have more accounts)
and i need a SQL query to show all accounts for the student...here is what i have, but it's not working...
"Select distinct s from Student s left join fetch s.accounts where s.id=:studId"
I should say that the Student has a field called accounts
And at the end of the query, i placed already ORDER BY and then the following code didn't work:
s.accounts.id
account.id
student.account.id
So...long story short...the query above, shows the accounts of the specific student...now i just need to order them by the id of the accounts
Any suggestions?
As OP confirmed adding it as answer.
select distinct s.id, s.name, a.id
from students s left outer join accounts a on s.id = a.id
order by s.id, a.id;
one student can have more accounts
So it's two tables:
student (id, name, ...)
accounts (id, student_id, ...)
I should say that the Student has a field called accounts
That makes no sense. By this you would store one account per student and several students could share one account. So I stick to the first statement that one student can have several accounts and the tables look more or less like I've shown above.
You want to see accounts for one student. So you select from accounts where the student ID matches:
select * from accounts where student_id = :studId order by account.id;
If you want to show student data along, you'd join the tables instead:
select *
from student s
left join accounts a on a.student_id = s.id
where s.id = :studId
order by a.id;

Where SQL column value not found in other column

I've read similar questions and I think I am doing it correct, but I just wanted to make sure my SQL is correct. (Still new to SQL)
I have 2 different tables
Students
id, name, address
Staff
id, name, address
I need to find the total number of students (who are not also staff)
SO I have the following SQL
create view nstudents as
select students.id
from students
LEFT JOIN staff ON staff.id = students.id;
Then I run the count(*) on the view.
Can someone confirm my SQL is correct or is there better way to do it?
Your LEFT JOIN doesn't eliminate students who are also staff, but it could be useful in achieving your goal. LEFT JOIN provides you with all results from the left table and matching results from the right table, or NULL results if the right table doesn't have a match. If you do this:
select count(*)
from students
LEFT JOIN staff ON staff.id = students.id
WHERE staff.id IS NULL;
I expect you'll get what you're looking for.
You might find it more natural to do something like this:
create view nstudents as
select s.id
from students s
where not exists (select 1 from staff st where st.id = s.id) ;
This should have the same performance as the left join.

SQL count after joining two tables

I am newbie to SQL, I would like to come up with a count, assume this example with 2 tables:
School(schoolID, name,....)
Student(StudentID, SchoolID, ...)
I tried:
SELECT COUNT(studentID)
FROM School s, Student t
WHERE s.schooldID = t.schoolID
How can I get a count of all students across all schools?
Since you have the school ID in the student table, it doesn't appear to me that you need to join to school at all. Just select a count from the student table and group by schoolID:
SELECT schoolID, COUNT(*) AS numStudents
FROM student
GROUP BY schoolID;
The only reason you'd need to join to School is if you want other information, such as school name and so on. If you just want the school id and number of students, the above will work.
To complete that last thought, possibly irrelevant to your question. If you did want school name, you just do an inner join and put school.name in your select statement, along with the count from the student table and group by school ID still:
SELECT s.name, st.COUNT(*) AS numStudents
FROM student st
JOIN school s ON s.id = st.schoolID
GROUP BY s.id;
If you want to get the count per school, you need a group by. Also, usually we prefer ANSI style joins, since in fact all database systems support them nowadays and they easier to read and maintain:
select count(t.studentID)
from Student t
join School s /* added join for your convenience, not necessary here */
on s.schooldID = t.schooldID
group
by t.schoolID