In terms of the contexts specifically, there's little difference. Most OpenGL implementations have most of the features of OpenGL 3.0+ even when using a legacy context, due to the way OpenGL extensions work.
If you're specifically asking about what features in OpenGL 3.0 are worth using, some of the best ones are geometry shaders and instancing, both of which are useful even for 2D graphics in certain circumstances. However, in most cases for simple 2D, all you're going to be doing is filling up a streaming vertex buffer every frame and making a single draw call, so there's really very little extra you're going to be doing.
In terms of 2D in OpenGL in general, just make sure you have a texture atlas (sprite sheet) so you very rarely need to change texture states. You want to avoid doing a draw call per sprite, as that is incredibly inefficient, and rather you want to batch together a lot of sprites and draw them all at once. Render with painter's algorithm, where "render" means pushing the geometry into a vertex buffer, and draw it at the end. Post-process as you see fit.