I have a MySQL query that:
- gets data from three tables linked by unique id’s.
- counts the number of games played in each category, from each user
- and counts the number of games each user has played that fall under the “fps” category
It seems to me that this code could be a lot smaller. How would I go about making this query smaller. http://sqlfiddle.com/#!2/6d211/1
Any help is appreciated even if you just give me links to check out.
Generally it’s a good idea to have your join logic as part of the
[Inner|Left] Joinclause, rather than as part of theWhereclause. In your case of simplifying the query, this cleans up your Where clause so that the query processor doesn’t apply filter conditions too early, which restricts what you want to do in more complex parts of the query (and impacts the overall performance of the query).By refactoring the join conditions, we can reduce the query to its core join across the three tables, and then add the join to the specialised subquery where the aggregation occurs. This results in only one nested query, which joins across the fewest tables needed.
Here’s what I came up with:
One difference between the original query (apart from the slight rename) is that the fps_count field has a value of 0 instead of NULL for players who haven’t played a single FPS game. Hopefully this isn’t so critical, but rather helps to add meaning to the query.
Lastly, I’m not sure about the context of how this is going to be used. In my opinion it’s probably trying to do too much in both listing every game played by every user (one objective) and summarising the categories of games played by each user (a separate objective). This means that the summary details are being repeated multiple times, e.g. for users playing multiple games of a particular category, which may not be ideal. My recommendation would be to separate these out into two separate queries, though I don’t know whether that would meet your specific needs.
Hope this helps.