Composer with same title but different Piece - sql

There are two tables to be used in this question they are
Piece(PNo, CNo, Title, Tune, Opus).
Composer(CNo, Last, First, Born, Died)
I have to List the composer’s first and last names, the titles of these music pieces along with the number of times the composer did that with the music piece title.
I am using Microsoft access
I have tried
SELECT PIECE.TITLE,COMPOSER.FIRST, COMPOSER.LAST, COUNT(*)
FROM PIECE, COMPOSER
GROUP BY PIECE.TITLE
HAVING COUNT(*) > 1
Help with this would be very much appreciated.

You need a join condition between the tables:
SELECT PIECE.TITLE, COMPOSER.FIRST, COMPOSER.LAST, COUNT(*)
FROM PIECE INNER JOIN
COMPOSER
PIECE.CNO = COMPOSER.CNO
GROUP BY PIECE.TITLE, COMPOSER.FIRST, COMPOSER.LAST
HAVING COUNT(*) > 1 ;

Related

Grouping by titles that are the same with the same (and then different) composers

I have two database tables,
PIECE (PNo, CNo, Title, Tune, Opus)
and
COMPOSER (CNO, LAST, FIRST, BORN, DIED)
are the ones I'm using for this query.
I need to Select Titles that are the same and with the same Composer. I need to list the titles and the number of versions of each. The next question requires the same listing if the Composers are different.
I tried:
SELECT TITLE, COUNT(*)
FROM PIECE, COMPOSER
WHERE PIECE.CNo = COMPOSER.CNo
GROUP BY TITLE
HAVING COUNT(*) > 1
ORDER BY COUNT(*);
Something is wrong with that query though. I am using SQLPLUS. Any help is appreciated.
The query for the question before it was to answer this:
"Different music pieces (with different PNo) may have the exact same title, list the titles of these music pieces. List these music titles, along with the number of versions (of music pieces) there are sharing the same title."
I used:
SELECT TITLE, COUNT(*)
FROM PIECE
GROUP BY TITLE
HAVING COUNT(*) > 1
ORDER BY COUNT(*);
Try this:
SELECT TITLE, COUNT(*)
FROM PIECE
GROUP BY TITLE
HAVING COUNT(*) > 1
MINUS
SELECT TITLE, count(*)
FROM PIECE P2
JOIN COMPOSER C2 ON P2.CNO = C2.CNO
GROUP BY TITLE, C2.CNO
HAVING COUNT(*) > 1
We find all titles that occur more then once then subtract the titles that have the same composer for all title versions. If you want more data then just the title, join back to the composers table to get more details for that title. We could also consider windowing functions in Oracle.
try replacing your query like this:
SELECT TITLE, COUNT(*) as Count
FROM PIECE, COMPOSER
WHERE PIECE.CNo = COMPOSER.CNo
GROUP BY TITLE
HAVING COUNT(*) > 1
ORDER BY count;

Access data source using SQL to show most recent entry per site

First of all I am a complete beginner to SQL and have been thrown in at the deep end a bit ! I'm learning as I go along and each mistake I make or question I ask will hopefully help me develop... please be kind :)
I have a working query that extracts electricty meter readings and other information. I am after finding the most recent reading for each site. This is the query at the moment :
PARAMETERS [Site Group] Text ( 255 );
SELECT
Lookup.Lookup_Name AS [Group],
Contacts.Name AS Site,
Points.Number AS MPAN,
Max(DataElectricity.Date) AS MaxDate,
DataElectricity.M1_Present,
DataElectricity.M2_Present,
DataElectricity.M3_Present,
DataElectricity.M4_Present,
DataElectricity.M5_Present,
DataElectricity.M6_Present,
DataElectricity.M7_Present,
DataElectricity.M8_Present,
DataElectricity.Direct
FROM
DataElectricity INNER JOIN (Lookup INNER JOIN (Points INNER JOIN Contacts ON Points.Contacts_Id = Contacts.Id) ON Lookup.Lookup_Id = Contacts.Group_1) ON DataElectricity.Point_Id = Points.Id
WHERE
((DataElectricity.Direct)='D')
GROUP BY
Lookup.Lookup_Name, Contacts.Name, Points.Number, DataElectricity.M1_Present, DataElectricity.M2_Present, DataElectricity.M3_Present, DataElectricity.M4_Present, DataElectricity.M5_Present, DataElectricity.M6_Present, DataElectricity.M7_Present, DataElectricity.M8_Present, DataElectricity.Direct
ORDER BY
Lookup.Lookup_Name, Contacts.Name, Max(DataElectricity.Date) DESC;
However this returns all the readings for a site rather than just the most recent... I'm sure this is simple but I can't figure it out.
Any advice or guidence is gratefully received :)
Can't you just use top 1 to get only the first result?
SELECT top 1 ...
I have evolved the code a bit further using caspian's suggestion of SELECT top 1... but am struggling to refine it further and produce the result I need.
PARAMETERS [Site Group] Text ( 255 );
SELECT
Lookup.Lookup_Name,
Contacts.Name AS Site,
Points.Number AS MPAN,
DataElectricity.M1_Present,
DataElectricity.M2_Present,
DataElectricity.M3_Present,
DataElectricity.M4_Present,
DataElectricity.M5_Present,
DataElectricity.M6_Present,
DataElectricity.M7_Present,
DataElectricity.M8_Present,
DataElectricity.Direct
FROM
(
SELECT TOP 1 DataElectricity.Date AS MaxDate,
DataElectricity.M1_Present,
DataElectricity.M2_Present,
DataElectricity.M3_Present,
DataElectricity.M4_Present,
DataElectricity.M5_Present,
DataElectricity.M6_Present,
DataElectricity.M7_Present,
DataElectricity.M8_Present,
DataElectricity.Point_id
FROM
DataElectricity
ORDER BY MaxDate DESC
)
DataElectricity INNER JOIN (Lookup INNER JOIN (Points INNER JOIN Contacts ON Points.Contacts_Id = Contacts.Id) ON Lookup.Lookup_Id = Contacts.Group_1) ON DataElectricity.Point_Id = Points.Id
WHERE
((Lookup.Lookup_Name)=Lookup_Name)
ORDER BY
Lookup.Lookup_Name, Contacts.Name, MaxDate DESC;
I do have a Google Drive file showing a small example of the data tables and desired result with hopfully a clear guide as to how the tables connect.
https://docs.google.com/file/d/0BybrcUCD29TxWVRsV1VtTm1Bems/edit?usp=sharing
The actual data contains hundreds of Site Groups each with potentially hundreds of sites.
I would like my end users to be able to select the Site Group name from the Lookup.Lookup_Name list and for it to return all the relevant sites and readings.
.... I really hope that makes sense !

BigQuery - Shuffle By error

I have a table of about 5M rows. Note this is just a poc. Ultimately we will need to be in the TB range. I am doing a self join to find permutations of products for a market basket analysis.
I need to find the number of times the combination occurs in a basket, the ratio of occurrences to total baskets, and the number of times the item occurs in all baskets. This is pretty standard. BigQuery does not support selects in the predicate of another select so I needed to create another join I suppose. Here's what I came up with -
select twoItem.upc1,twoItem.upc2,twoItem.twoItemOccurrences, totalUpc.totalUpcCount
from
(
select purchase1.upc as upc1,purchase2.upc as upc2,count(upc1) as twoItemOccurrences
from
conagra.purchase as purchase1
join each conagra.purchase as purchase2
on purchase1.upc = purchase2.upc
group by upc1,upc2
) as twoItem
JOIN EACH
(
select purchase3.upc as upc3, count(*) as totalUpcCount
from conagra.purchase as purchase3
group by upc3
) as totalUpc
on totalUpc.upc3 = twoItem.upc1
LIMIT 50;
I get the following error:
SHUFFLE BY may only be applied to parallelizable queries, but query is not parallelizable: (SELECT * FROM (SELECT [purchase3.upc] AS [upc3], COUNT(*) AS [totalUpcCount]...
Maybe an unpublished limitation?
Any help would be appreciated.
Try running these with GROUP EACH BY on your inner queries. We'll improve the response message for queries like this.

sqlzoo track join exercise

I've found a great site to practice sql - http://sqlzoo.net. my sql is very weak that is why i want to improve it by working on the exercises online. But i have this one problem that I cannot solve. can you please give me a hand.
3a. Find the songs that appear on more than 2 albums. Include a count of the number of times each shows up.
album(asin, title, artist, price, release, label, rank)
track(album, dsk, posn, song)
my answer is incorrect as i ran the query.
select a.song, count(a.song) from track a, track b
where a.song = b.song
a.album != b.album
group by a.song
having count(a.song) > 2
thanks in advance! :D
I realize this answer may be late but for future reference to anyone taking on this tutorial the answer is as such
SELECT track.song, count(album.title)
FROM album INNER JOIN track ON (album.asin = track.album)
GROUP BY track.song
HAVING count(DISTINCT album.title) > 2
Some things that my help you in your quest for this query is that what to group by is usually specified by the word each. As per the tip presented in the previous answers you want to select by distinct albums, SINCE it mentioned in the database description that album titles would be repeated when the two tables are joined
Your original answer is very close, with the GROUP BY and HAVING clause. What is wrong, is just that you don't need to join the track table against itself.
SELECT song, count(*)
FROM track
GROUP BY song
HAVING count(*) > 2
Another answer here uses COUNT(DISTNCT album), which is necessary only if a song can appear on an album more than once.
If they support nested querys, you can:
Select song, count(*)
from(
select a.song
from track a
group by a.song, a.album
having count(*) > 1
)
group by song
or(best way to write it)if they support this syntax:
select a.song, count(distinct a.album)
from track a
group by a.song
having count(distinct a.album) > 1

Creating Report, repetition in report output, Ms Access SQL

SELECT NMC.*, Exam.Final_Exam_Level
FROM
(SELECT Technicians.Technician_ID AS Technician_ID,
Technicians.First_Name AS First_Name,
Technicians.Surname AS Surname,
MAX(New_Models.Date_Issued) AS Last_Course_Date,
MAX(New_Models.Issue) AS Last_Issue,
MAX(New_Models.Model_ID) AS Last_Model_ID,
Technicians.Course_Level AS No_Training_Courses
FROM New_Models, New_Models_Allocation, Technicians
WHERE New_Models.Model_ID=New_models_Allocation.Model_ID
And Technicians.Technician_ID=New_Models_Allocation.Technician_ID
GROUP BY Technicians.Technician_ID, Technicians.Course_Level, First_Name, Surname
ORDER BY MAX(New_Models.Model_ID) DESC)
AS NMC
INNER JOIN (SELECT Technicians.Technician_ID, COUNT(*) AS Final_Exam_Level
FROM Technicians, Exams, Exam_Allocation
WHERE (Technicians.Technician_ID)=Exam_Allocation.Technician_ID
And ((Exams.Exam_ID)=Exam_Allocation.Exam_ID)
And (Exams.Date_Taken)<=#12/31/2010#
GROUP BY Technicians.Technician_ID, Technicians.Course_Level
ORDER BY Technicians.Technician_ID)
AS Exam ON Exam.Technician_ID=NMC.Technician_ID;
This query shows each technician, Last Exam, Last New_Model, Last course.
SELECT Technicians.Technician_ID, Jobs.Job_ID, Jobs.Date_Occured, Fix
FROM Technicians, Jobs, Tech_Allocation, Recovery
WHERE Technicians.Technician_ID=Tech_Allocation.Technician_ID
And Jobs.Job_ID=Tech_Allocation.Job_ID
And Jobs.Job_ID=Recovery.Job_ID
And Jobs.Date_Occured>=#1/1/2010#
And Jobs.Date_Occured<=#12/31/2010#
ORDER BY Fix;
This query shows the jobs each technician has done.
However, when creating a report in Ms Access, the jobs are repeated. Hence, instead of a technician having done 3 jobs, it shows 12 for example. Although when running the second query itself, results aren't repeated.
Any Help?
For obvious reasons, I don't usually read other people's SQL queries, but your example was very well formatted. Is this the problem?
INNER JOIN (SELECT Technicians.Technician_ID, COUNT(*) AS Final_Exam_Level
...
GROUP BY Technicians.Technician_ID, Technicians.Course_Level
These 2 lines are from the 2nd subquery of your first query. You have 1 index field (Technician_ID), but 2 grouping fields (Technician_ID and Course_Level). This would produce results like:
Technician_ID Final_Exam_Level
Bob 5
Bob 4
Nadine 5
I recommend either removing Course_Level from the Group By or adding it to the Select row.