I have 3 tables, players, matches, wins. I want to make a query that retrieves back the player id, the name, the amount of matches he played and how many wins he got.
the matches table keeps track of the round it's in, the players who take part (p_one_id and p_two_id) while the wins table keeps track of the match id, to see who he won against, and the player id.
if I do
SELECT players.id, players.name, COUNT(matches.*) as matches FROM players, matches WERE matches.p_one_id = players.id GROUP BY players.id
It works fine, at least from my basic tests ( but that doesn t also check for wins) but if I do
SELECT players.id, players.name, COUNT(matches.*) as matches, COUNT(wins.*) AS wins FROM players, matches, wins WERE matches.p_one_id = players.id AND wins.p_id = players.id GROUP BY players.id
I get nothing, one reason is that there's no wins, but then I d only get the guys who won, I can t make a sub query either, since I can't use the player id inside of the subquery, at least not from my knowledge). Anyone know what query I'd need for my result?
I would suggest using a LEFT JOIN instead of the cross join / where clause option. You may also wish to count the matches where the player was "player 2". Something along the lines of:
SELECT
p.id,
p.name,
count(m1.*) + count(m2.*) as matches,
count(w.*) as wins
FROM players p
LEFT JOIN matches m1
ON m.p_one_id = p.id
LEFT JOIN matches m2
on m.p_two_id = p.id
LEFT JOIN wins w
ON w.p_id = p.id
GROUP BY p.id, p.name
User outer joins. The join syntax you're using is eliminating players unless they have both wins and matches.
SELECT players.id, players.name,
COUNT(matches.p_one_id) as matches,
COUNT(wins.p_id) AS wins
FROM players
LEFT JOIN matches
on matches.p_one_id = players.id
LEFT JOIN wins
on wins.p_id = players.id
GROUP BY players.i, players.name
This will return all players, matches, and wins.
Related
How I can get top 10 scorers by seasons.
So it shows last season top 10 scorers...
I've tryed left join into table, but it goes broken showing 2 player and counts all goals to first player.
My sqlfiddle:
http://sqlfiddle.com/#!9/b5d0a78/1
You got it almost right.
You want to group match_goals by player ID (match_player_id), but then you should not select goal_minute or any other per goal data.
After grouping by player, then you can create a column for COUNT(match_player_id) this will give you the number of goals, you can also use this column to order the results.
Your joins and conditions are correct I think.
EDIT
I think your schema needs a few tweaks: check this http://sqlfiddle.com/#!9/f5a75b/2
Basically create direct relations in the match_players and match_goals to the other tables.
I think the query you want looks like this:
SELECT p.*, count(*) as num_goals
FROM match_goals g INNER JOIN
match_players p
ON g.match_player_id = p.id INNER JOIN
matches m
ON m.id = p.match_id
WHERE p.is_deleted = 0 AND
g.is_own_goal = 0 AND
m.seasion_id = <last season id>
GROUP BY p.id
ORDER BY num_goals DESC
LIMIT 10;
Note that the teams table is not needed. The SELECT p.* is allowed because p.id (the GROUP BY key) is unique.
I have this schema:
CLUB(Name, Address, City)
TEAM(TeamName, club)
PLAYER(Badge, teamName)
MATCH(matchNumber, player1, player2, club, winner)
I need to make this query:
For each club, find the number of players in that club that have won
at least two games.
I wrote this:
SELECT teamName
From TEAM t join Match m1 on t.club=m1.club
WHERE Q2 >= ALL Q1
Q1:
SELECT Count (Distinct winner)
FROM MATCH
WHERE match m join player p on m. winner=player.badge
GROUP BY teamName
Q2:
SELECT Count (distinct winner)
FROM match m2
WHERE m2.club=m1.club
I don’t know if it is correct, however I heard that using this form where I confront two counts is not the best. Why?
Try something like this:
SELECT club, COUNT(*) as PlayerCount
FROM (SELECT club, winner
FROM match
GROUP BY club, winner
HAVING COUNT(*) > 1) a
GROUP BY club
The inner query should limit results to club/player combinations that have 2 or more wins, and the outer query will count the number of these players per club.
I don’t know if it is correct, however I heard that using this form where I confront two counts is not the best. Why?
Comparing two count subqueries is fine if you need to, but a good rule of thumb is to hit each table as few times as possible. Using multiple subqueries will end up hitting each table multiple times, and will usually result in longer execution times.
Try this query
SELECT t.club, COUNT(*)
FROM TEAM t
JOIN PLAYER p ON p.teamName = t.TeamName
JOIN (
-- Won at least 2 matches.
SELECT club, winner, COUNT(*) AS TheCount
FROM MATCH
GROUP BY club, winner
HAVING COUNT(*) > 1
) w ON w.winner = p.badge AND w.club = t.club
GROUP BY t.club
I have two tables, one called players, one called matches.
The players table contains 2 columns: id, name
The matches table contains 5 columns: player1, player2, goalsforplayer1, goalsforplayer2, matchid
Looking for the right query to get the names (not player id) and the result of matches, ideally comparing the goalsforplayer1 and goalsforplayer2 to get either a winner or a draw in each match. Essentially making a list of results.
Is something like this possible using a mysql query?
You should use two inner join on players
select
b.name as nameplayer1
, c.name as nameplayer2
, a.goalsforplayer1
, a.goalsforplayer2
, a.matchid
from matches as a
inner join players as b on a.player1 = b.id
inner join players as c on a.player2 = c.id
This should be what you're looking for (To get a list of players, and their total match results), and should guide you in the correct direction:
SELECT p.*,
(COUNT(CASE WHEN m1.goalsforplayer1 > m1.goalsforplayer2 THEN 1 ELSE NULL END) +
(COUNT(CASE WHEN m2.goalsforplayer2 > m2.goalsforplayer1 THEN 1 ELSE NULL END)
) AS wins
FROM players p
INNER JOIN matches m1 ON p.id = m1.player1
INNER JOIN matches m2 ON p.id = m2.player2
GROUP BY p.id
Join on the matches table, and group by the ID. Use aggregation functions (COUNT here), to get the total number of matches that a player has won. If you want draws, simply modify the queries.
If you're looking for simple results (With players from each side), then use this:
SELECT p1.name AS player1, p2.name AS player2, m.goalsforplayer1, m.goalsforplayer2, m.matchid
FROM matches m
INNER JOIN players p1 ON p1.id = m.player1
INNER JOIN players p2 ON p2.id = m.player2
I need to count the amount of games a player has played by counting the number of times his player ID appears on another table, here is the code I've been playing with:
SELECT players.playerID, players.fName, players.lName, matches.playerID, COUNT(matches.playerID) AS 'gamesPlayed'
FROM players
INNER JOIN matches
ON matches.playerID = players.playerID
WHERE players.playerID=matches.playerID
ORDER BY gamesPlayed"
Currently there is 2 players having played 2 matches.
The current code returns 1 player having played 4 matches.
I am trying to get the COUNT(matches.playerID) to return only matches where the players.playerID = matches.playerID.
Any help is much appreciated!
You need to GROUP BY:
SELECT p.playerID, p.fName, p.lName, COUNT(*) AS gamesPlayed
FROM players p INNER JOIN matches m
ON p.playerID = m.playerID
GROUP BY p.playerID, p.fName, p.lName
ORDER BY gamesPlayed
If you want even players who have played zero games, then:
SELECT p.playerID, p.fName, p.lName, COUNT(m.playerID) AS gamesPlayed
FROM players p LEFT JOIN matches m
ON p.playerID = m.playerID
GROUP BY p.playerID, p.fName, p.lName
ORDER BY gamesPlayed
The reason I use COUNT(m.playerID) instead of COUNT(*) in the above is because COUNT(*) will always be at least one in this instance, while COUNT(m.playerID) can be zero if the only matched value is NULL.
At first place: your query lacks GROUP BY, at second - please check what argument COUNT accepts (in this query it's no different from COUNT(*)) – zerkms
I have 2 SELECT queries one which retrieve a team and one which count how many players there are in that team. How can i add that count query in to the first data select query? i've tried by union, but does not work since they do not have the same number of columns.
SELECT Subteams.id, Teams.name, Games.name as 'game'
FROM Subteams, Games, Teams
WHERE Subteams.gameId = Games.id
AND Subteams.teamId = Teams.id
SELECT COUNT(Players.subTeamId) as 'count'
FROM Subteams, Games, Teams, Players
WHERE Subteams.gameId = Games.id
AND Subteams.teamId = Teams.id
AND Players.subTeamId = Subteams.id
ORDER BY Players.id
Just add the columns from the other tables to the COUNT() query.
SELECT Subteams.id, Teams.name, Games.name as game, COUNT(Players.subTeamId) as 'count'
FROM Subteams
JOIN Games ON Subteams.gameId = Games.id
JOIN Teams ON Subteams.teamId = Teams.id
LEFT JOIN Players ON Players.subTeamId = Subteams.id
GROUP BY Subteams.id
ORDER BY Subteams.id
I've also used LEFT JOIN so you'll get 0 for teams with no players.