I have 3 tables in a MySQL database,
Author
Book
Author_has_Book.
The author has two columns
idauthor
name
Book also has two columns
idbook
name
Author_has_Book also has two columns
foreign keys of an author and a book book_idbook
author_idauthor.
I have successfully inserted an author and a book into both tables and I have entered their keys into the join table.
Now how do I use this join table to get all books by a certain author, or all authors for a book? Is this accomplished with joins?
edit: The suggested duplicate is not the same question.
It will get you all records
SELECT Author.*
FROM Author Author
INNER JOIN Author_has_Book AuthorHasBook
ON Author.idauthor = AuthorHasBook.author_idauthor
INNER JOIN Book Book
ON AuthorHasBook.book_idbook = Book.idbook
and if you wish to select any specific author, you just need to mention it in where clause, see example below:
SELECT Author.*
FROM Author Author
INNER JOIN Author_has_Book AuthorHasBook
ON Author.idauthor = AuthorHasBook.author_idauthor
INNER JOIN Book Book
ON AuthorHasBook.book_idbook = Book.idbook
WHERE Author.idauthor = 'your author id'
Try this query
select a.name,c.name from book a
join Author_has_Book b on a.idbook=b.idbook
join author c on b.idauthor=c.idauthor
Related
I am haveing a lot of trouble trying to work out this question
Write a query to show the number of authors who have written a book
Author(AuthorID, AuthorName, Address, TelephoneNo, PublisherCode)
Book (BookID, Name, ReleaseDate, Price, AuthorID)
I have
SELECT a.AuthorName, COUNT(b.*) AS ‘number of books written’
FROM Author a JOIN Book b ON a.AuthorID = b.BookID
GROUP BY a.AuthorName;
Which counts the number of books each author has written.
This is not the correct I know, but I can not figure it out??
Assuming the requirement is to count authors that have at least one book, the simplest query to satisfy that would be:
SELECT COUNT(DISTINCT b.authorid)
FROM book b
We probably want to assign an alias (name) to the returned column:
SELECT COUNT(DISTINCT b.authorid) AS `count_of_authors_who_have_at_least_one_book`
FROM book b
We could also do a join to the author table, but that isn't necessary here, unless there are values of authorid in the book table that don't appear in the author table (i.e. there's not a foreign key constraint, or referential integrity is not enforced)
Queries to get authors that have two or more books would be a bit more complicated:
SELECT COUNT(*)
FROM ( -- authors of two or more books
SELECT b.authorid
FROM book b
GROUP
BY b.authorid
HAVING COUNT(1) >= 2
) c
If we want authors that have EXACTLY one book (not two or more) we can tweak the condition in the HAVING clause:
SELECT COUNT(*) AS `count_authors_of_exactly_one_book`
FROM ( -- authors of exactly one book
SELECT b.authorid
FROM book b
GROUP
BY b.authorid
HAVING COUNT(1) = 1
) c
You were pretty close. You need to join on the author ID. You are currently mixing the author and book ID's, which won't match correctly.
SELECT
a.AuthorName,
COUNT(b.*) AS ‘number of books written’
FROM Author a
JOIN Book b ON a.AuthorID = b.AuthorID
GROUP BY a.AuthorName;
If you wanna get just a number that indicate total count of Author that wrote at least on book use below query
select count(*) as author_count from Author where exists (select 1 from Book where Book.AuthorID = Author.AuthorID)
i am currently working with a MYSQL-Database whichhas three tables:
Books, Keywords and KeywordAssignment.
The tables Books and Keywords are in a many to many relationship therefore the table KeywordAssignment.
Now to my question: I want to search for a book with multiple (max: up to ten) keywords.
I've already tried a self join:
SELECT BookID
FROM Keywords K1 INNER JOIN
Keywords K2
ON K1.KeywordAssignmentID=K2.KeywordAssignmentID INNER JOIN
KeywordAssignment
ON KeywordAssignment.KeywordAssignmentID=K1.KeywordAssignmentID INNER JOIN
Books
ON KeywordAssignment.BookID=Books.BookID
WHERE K1.Keyword='Magic' AND K2.Keyword='Fantasy'
The problem is it only works if the given Keyword are in the right order. If they aren't there are more than one.
I appreciate your help thank you very much!
You need to GROUP BY BookID and a HAVING clause with the condition that both keywords are linked to that BookID:
SELECT b.BookID, b.Title
FROM Books b
INNER JOIN KeywordAssignment ka ON ka.BookID = b.BookID
INNER JOIN Keyword k ON k.KeywordID = ka.KeywordID
WHERE k.Keyword IN ('Magic', 'Fantasy')
GROUP BY b.BookID, b.Title
HAVING COUNT(DISTINCT k.Keyword) = 2
This code will return books that are linked to both 'Magic' and 'Fantasy'.
If you want either of the 2 keywords then remove the HAVING clause.
If I understand your question correctly, you want to query for books that have multiple key words. The key word there is have. I don't have MYSQL but the query should look something like this:
SELECT B.BookID, COUNT(*) as NumberOfKeywords FROM Books B
INNER JOIN KeywordAssignment KA
ON B.BookID = KA.BookID
INNER JOIN Keywords K
ON KA.KeywordID = K.KeywordID
GROUP BY B.BookID
HAVING NumberOfKeywords > 0 AND NumberOfKeywords <= 10
What we are doing is grouping by each book and then selecting the ones that have more than 0 keywords and less than 10.
Say I have a database of publishers, who employ authors, who write books.
Or to phrase it another way, each book, is written by an author, who works for a publisher.
publishers: id
authors: id, publisher_id
books: id, author_id
I know how to get a list of publishers with how many authors each employs, from this question.
How do I get a list of publishers with how many books each has published?
How can I get both - publishers, each with number of authors and number of books?
try this
SELECT COUNT(DISTINCT b.`id`) noofbooks,COUNT(DISTINCT au.id) noofauthers,pub.id publisher FROM publisher pub
INNER JOIN auther au ON au.`pub_id`= pub.`id`
INNER JOIN books b ON b.`aut_id` = au.`id` GROUP BY pub.id
You need a three table join
SELECT publisher.id, count(*) from publisher
INNER JOIN author on publisher.id = author.publisher_id
INNER JOIN book on author.id = book.author_id GROUP BY publisher.id;
You just need to fire a simple sql join query for that like as follow.
SELECT p.publishers , COUNT(a.authors) totalAuthors, COUNT(b.books) TotalBooks
FROM publishers AS p,authors AS a ,books AS b
WHERE p.publishersid = a.publishersid
AND a.authorsid = b.authorsid
GROUP BY p.publishersid;
I ended up with something similar to bhanu's answer:
SELECT publishers.*,
COUNT(DISTINCT authors.id) AS 'author_count',
COUNT(DISTINCT books.id) AS 'book_count'
FROM publishers
LEFT JOIN authors ON (authors.publisher_id = publishers.id)
LEFT JOIN books ON (books.author_id = authors.id)
GROUP BY publishers.id;
I have 2 tables:
authors table:
id_author
author(author name in this column)
author_ind table:
id_book
id_author
My query is:
SELECT author
FROM authors
LEFT JOIN author_ind
ON author_ind.id_book = author_ind.id_author
LEFT JOIN authors author
ON author_ind.id_author = authors.id_author
WHERE author_ind.id_book=%d
I need to get the authors info from the authors table based on the id_book from the author_ind table. MYSQL error #1052 - Column 'author' in field list is ambiguous.
Little help please:)
Update: thank you everyone. correct query:
SELECT authors.author
FROM authors, author_ind
WHERE author_ind.id_book =14
AND authors.id_author = author_ind.id_author
14 is just a book id, I used it to test if it worked instead of %d
Based on what you're trying to get, you've made this more complex than it needs to be. You don't need to do a 2nd join on the authors table. Also, if you only want authors who have a record in the author_ind table, you can do a INNER JOIN instead of LEFT JOIN:
SELECT author
FROM authors
INNER JOIN author_ind
ON authors.id_author = author_ind.id_author
WHERE author_ind.id_book=%d
I have a database having the following structure. Each book can have multiple authors, and each author can write multiple books.
[book:book_id, book_name, book_price]
[author: author_id, author_name]
[link:book_id, author_id]
{book_id's and author_id's are linked. the complete structure is shown here: http://i.stack.imgur.com/vIFNU.png}
Now each book has a price (currency). 30% of the price should be equally distributed to each author who have contributed to the book.
My question is how to find the total payment for each author for a particular year.
[I thought of a solution my self. I could do only up to step 1. If you can provide me some hints or materials where I can find how do such manipulations, it would be very helpful]
Algorithm of my solution is:
So for each book_id, I need to find the number of author_id's in the middle table who has the same book_id. (could do it by query)
If I divide the book_price by number_of_author_in_book and multiply it with 30/100, I get the money for that book that will go to the each author's account for that book (say payment_of_one_author_in_book)
For each author_id in the middle table, I look up for the corresponding book_id and add the payment_of_one_author_in_book for that author_id to a new variable (author_payment_this_year) corresponding to the author ID, if the year matches to the query year.
Thanks in advance
This example includes aliases and subqueries.
SELECT
a.author_id,
a.author_name,
SUM(share.auth_share) AS author_total
FROM (link l
INNER JOIN (
SELECT
b.book_id,
( [b.book_price] * 0.3 ) / [no_auth] AS auth_share
FROM book b
INNER JOIN (
SELECT
l.book_id,
COUNT(l.author_id) AS no_auth
FROM link l
GROUP BY l.book_id) AS ac
ON b.book_id = ac.book_id) AS share
ON l.book_id = share.book_id)
INNER JOIN author a
ON l.author_id = a.author_id
GROUP BY a.author_id,a.author_name
SELECT author.AuthorId, author.Author_name, book.Book_Name, book.Book_Price, [Book_Price]/DCount("[Author_id]","[Link]","[Book_id]=" & [Book_Id]) AS Share
FROM (author INNER JOIN link AS link_1 ON author.AuthorId = link_1.Author_id) INNER JOIN book ON link_1.Book_id = book.Book_Id;
Basically, it is just a join of the three tables. The only tricky bit is using DCount function to add up how many authors in Link share this book_ID