During server startup, ServerCommandManager() calls CommandBase.setCommandListener() with itself as the argument.
This means that the CommandBase class holds a staic reference to the command manager, which holds a reference to the server.
As the server holds references to many game objects, this link keeps a fairly large amount of memory from being garbage collected if the application continues, which is the case for the single-player client.
This can be seen by starting the single-player client, loading a world, and then quitting to the title screen, then taking a heap dump of the application.
While this is not a permanent leak, as the field will eventually be overwritten, it causes memory to stay in use a lot longer than it would otherwise, and increases memory demands to load subsequent worlds.
A solution here would be to add a call to CommandBase.setCommandListener(null) in MinecraftServer.stopServer(), either directly or through ServerCommandManager.
Appears to have already been fixed in 17w45a with the command system rewrite (brigadier).
This was already partially reported in MC-101260 but since that one also mentions another leak (which isn't fixed), I'll just split that off to this issue and resolve this as fixed.