使用:http://dev.mysql.com/doc/sakila/en/
我试图写一个查询来计算每个演员按类别行事的电影数量。
非常感谢任何指示或建议。
到目前为止,这是我的代码(当我拿出第二个LEFT JOIN部分时,它正确计算了一个类别的影片):
SELECT actor.first_name, actor.last_name,
COUNT(subset.film_id) AS action,
COUNT(subset2.film_id) AS animation
FROM actor
LEFT JOIN (
SELECT film.film_id, actor.actor_id
FROM actor
INNER JOIN film_actor
ON film_actor.actor_id = actor.actor_id
INNER JOIN film
ON film.film_id = film_actor.film_id
INNER JOIN film_category
ON film_category.film_id = film.film_id
INNER JOIN category
ON category.category_id = film_category.category_id
WHERE category.name = 'Action') AS subset
ON subset.actor_id = actor.actor_id
LEFT JOIN (
SELECT film.film_id, actor.actor_id
FROM actor
INNER JOIN film_actor
ON film_actor.actor_id = actor.actor_id
INNER JOIN film
ON film.film_id = film_actor.film_id
INNER JOIN film_category
ON film_category.film_id = film.film_id
INNER JOIN category
ON category.category_id = film_category.category_id
WHERE category.name = 'Animation') AS subset2
ON subset2.actor_id = actor.actor_id
GROUP BY actor.actor_id
ORDER BY actor.last_name ASC;
答案 0 :(得分:1)
如果您只想获得每个演员和类别的电影数量,那么您所获得的查询似乎非常复杂。
此查询:
SELECT
actor.first_name, actor.last_name, category.name,
COUNT(*) as CountPerCategory
FROM actor
JOIN film_actor ON film_actor.actor_id = actor.actor_id
JOIN film ON film.film_id = film_actor.film_id
JOIN film_category ON film_category.film_id = film.film_id
JOIN category ON category.category_id = film_category.category_id
GROUP BY actor.first_name, actor.last_name, category.name;
会给你一个输出:
Firstname, Lastname, Category, CountPerCategory
Clint Eastwood Animation 1
Clint Eastwood Action 15
但是如果你想要不同列中每个类别的计数,你可以利用MySQL为真实条件返回1的事实,并测试该类别是否匹配并使用sum(这也可能不包括案例表达式)一种更便携的方式),像这样:
SELECT
actor.first_name, actor.last_name, category.name
, SUM(category.name = 'Animation') as CountOfAnimation
, SUM(category.name = 'Action') as CountOfAction
FROM actor
JOIN film_actor ON film_actor.actor_id = actor.actor_id
JOIN film ON film.film_id = film_actor.film_id
JOIN film_category ON film_category.film_id = film.film_id
JOIN category ON category.category_id = film_category.category_id
GROUP BY actor.first_name, actor.last_name, category.name;
会产生如下结果:
Firstname, Lastname, CountOfAnimation, CountOfAction
Clint Eastwood 1 15
请注意,如果一部电影属于多个类别,则每个类别都会计算一次,这可能是您想要的(或不是)。
答案 1 :(得分:0)
这应该为您提供所有参与者的计数,包括与之关联的所有类别:
SELECT actor.first_name, actor.last_name, category.name
, COUNT(DISTINCT film.film_id)
FROM actor
LEFT JOIN film_actor ON film_actor.actor_id = actor.actor_id
LEFT JOIN film ON film.film_id = film_actor.film_id
LEFT JOIN film_category ON film_category.film_id = film.film_id
LEFT JOIN category ON category.category_id = film_category.category_id
GROUP BY actor.first_name, actor.last_name, category.name
;
如果您只想要特定的,请在GROUP BY
行之后添加:
HAVING category.name IN ('Action', 'Animation')
如果您只想要拥有这些类别的演员,请将LEFT JOIN
更改为INNER JOIN
和/或将上述HAVING更改为WHERE(并相应地重新定位)。
答案 2 :(得分:0)
我同意,该查询看起来非常复杂,并且通过使用2个派生表,它也可能运行缓慢。此查询将在每个类别中提供唯一的电影,并且不会复制结果,因为没有多对多的连接。 它会在您添加类别时减慢,但是因为它必须多次扫描表格,但它会给出准确的结果,只要您的表格不是太大就应该没问题。
你可能不需要不同的,但如果出于某种原因,某人在电影上有两次相同的类别(或类似的东西),这将消除错误的空间。
select a.first_name, a.last_name
, (
select count(distinct f.id)
from film f
join film_actor fa on fa.film_id=f.film_id
join film_category fc on fc.film_id=f.film_id
join category c ON c.category_id = fc.category_id
where c.name='Animation'
and fa.actor_id=a.actor_id
) as unique_animation_films
, (
select count(distinct f.id)
from film f
join film_actor fa on fa.film_id=f.film_id
join film_category fc on fc.film_id=f.film_id
join category c ON c.category_id = fc.category_id
where c.name='Action'
and fa.actor_id=a.actor_id
) as unique_action_films
from actor a