我需要创建选择next的选择:
我有三张桌子:演员,工作室和电影。演员和电影有多对多的关系,制片厂和电影有多到多的关系.演员和工作室没有关系。Films_actors表也有字段“酬金”。
所以我可以选择制片厂,电影和酬金
SELECT studios.title, films.title, films_actors.honorarium
FROM studios
JOIN studios_films ON studios.id = studios_films.studio_id
JOIN films ON films.id = studios_films.film_id
JOIN films_actors ON films.id = films_actors.film_idMySQL数据库的转储是下一个(http://www.sqlfiddle.com/#!2/17ff2):
CREATE TABLE IF NOT EXISTS `actors` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`surname` varchar(255) DEFAULT NULL,
`name` varchar(255) DEFAULT NULL,
`birthday` date DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB;
CREATE TABLE IF NOT EXISTS `studios` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`title` varchar(255) DEFAULT NULL,
`founded` year(4) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB;
CREATE TABLE IF NOT EXISTS `studios_films` (
`studio_id` int(11) NOT NULL,
`film_id` int(11) NOT NULL,
KEY `studio_id` (`studio_id`),
KEY `film_id` (`film_id`)
) ENGINE=InnoDB;
CREATE TABLE IF NOT EXISTS `films` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`title` varchar(255) DEFAULT NULL,
`director` varchar(255) DEFAULT NULL,
`created` year(4) DEFAULT NULL,
`budget` decimal(12,2) DEFAULT NULL,
`box_office` decimal(13,2) DEFAULT NULL,
`duration` time DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB;
CREATE TABLE IF NOT EXISTS `films_actors` (
`film_id` int(11) NOT NULL,
`actor_id` int(11) NOT NULL DEFAULT '0',
`honorarium` decimal(10,0) DEFAULT NULL,
PRIMARY KEY (`film_id`,`actor_id`),
KEY `actor_id` (`actor_id`)
) ENGINE=InnoDB;
ALTER TABLE `studios_films`
ADD FOREIGN KEY (`studio_id`) REFERENCES `studios` (`id`),
ADD FOREIGN KEY (`film_id`) REFERENCES `films` (`id`);
ALTER TABLE `films_actors`
ADD FOREIGN KEY (`film_id`) REFERENCES `films` (`id`),
ADD FOREIGN KEY (`actor_id`) REFERENCES `actors` (`id`);谢谢你帮忙!
发布于 2014-11-03 15:53:37
如果没有样本数据,这是很难进行验证的,但我建议您只需一步一步地进行,这就是我将如何帮助回答您的问题。第一部分是简单的,我希望你至少可以选择一个工作室的标题。
对于第二种方法,您可以在酬金列上使用SUM()函数,并按studio id进行分组以获得每个列的总数。您可以使用WHERE子句确保电影日期在过去10年内(这是我能找到的唯一日期字段,所以我假设它就是您所需要的)。看起来是这样的:
SELECT s.title, SUM(fa.honorarium) AS totalHonorarium
FROM studios s
JOIN studios_films sf ON sf.studio_id = s.id
JOIN films f ON f.id = sf.film_id
JOIN films_actors fa ON fa.film_id = f.id
WHERE f.created >= (SUBDATE(CURDATE(), INTERVAL 10 YEAR))
GROUP BY s.id;下一部分,你问我的问题有些含糊不清。你想要所有工作室的平均酬金,还是每个工作室的平均金额?你也没有具体说明“过去十年”,这是所有其他东西都在使用的。我会在收到你的回复后编辑这个答案。
要获得工作室在过去10年中创建的电影数量,只需调整上面的查询以包含COUNT()函数即可。在这里,您希望为每个film_ids计算不同的studio_id。所以试试这个:
SELECT s.title, SUM(fa.honorarium) AS totalHonorarium, COUNT(DISTINCT f.id) AS totalFilms
FROM studios s
JOIN studios_films sf ON sf.studio_id = s.id
JOIN films f ON f.id = sf.film_id
JOIN films_actors fa ON fa.film_id = f.id
WHERE f.created >= (SUBDATE(CURDATE(), INTERVAL 10 YEAR))
GROUP BY s.id;最后,要获得每场电影的酬金(这就是我对你问题的理解),你需要另一个查询,因为你的分组将会改变。它应该是这样的:
SELECT s.title, f.id, SUM(fa.honorarium) AS totalHonorariumForFilm
FROM studios s
JOIN studios_films sf ON sf.studio_id = s.id
JOIN films f ON f.id = sf.film_id
JOIN films_actors fa ON fa.film_id = f.id
WHERE f.created >= (SUBDATE(CURDATE(), INTERVAL 10 YEAR))
GROUP BY s.id, f.id;这是一个用于这些例子的SQL Fiddle,其中有一些我自己输入的虚拟数据。如果你有什么问题,请告诉我,如果你在向我解释你的需要方面仍然有困难,我可以帮你解决。
编辑
还可以在create语句中使用外键,而不是更改表。这有助于避免某些插入问题。我做了一些建议编辑的这里。
编辑2
对于编辑,您可以使用与第一个查询相同的联接,并实现一些不同的聚合函数来获取所需的值。由于每个工作室仍然获得这些值,所以分组保持不变。试试这个:
SELECT s.title, COUNT(DISTINCT f.id) AS totalFilms, COUNT(fa.film_id) AS amountOfHonorarium, SUM(fa.honorarium) AS totalHonorarium, AVG(fa.honorarium) AS averageHonorarium
FROM studios s
JOIN studios_films sf ON sf.studio_id = s.id
JOIN films f ON f.id = sf.film_id
JOIN films_actors fa ON fa.film_id = f.id
WHERE f.created >= (SUBDATE(CURDATE(), INTERVAL 10 YEAR))
GROUP BY s.id;这是SQL Fiddle,里面有这个。就每部电影的酬金而言,我认为你可以按电影的标题和酬金的总和,一部接一部地说:
SELECT f.title, SUM(fa.honorarium) AS honorariumForFilm
FROM films f
JOIN films_actors fa ON fa.film_id = f.id
GROUP BY f.id;如果这样做有更好的效果,请告诉我。如果混乱仍然存在,我会继续帮助你。
https://stackoverflow.com/questions/26717186
复制相似问题