A Python “no handles with labels found to put in legend” error message can be quite perplexing. Part of this confusion stems from the fact that the terminology is somewhat adjacent to that found within the standard Python library.
The error message is typically associated with a plotting library for Python called Matplotlib. And Matplotlib is itself built on an advanced numerical mathematics extension called NumPy. All of this means that a “no handles with labels found to put in legend” error will typically be somewhat confusing at first glance thanks to how far it’s removed from standard python libraries. However, you can generally track the potential causes for this error down to a few common issues.
A “no handles with labels found to put in legend” error stems from Matplotlib’s pyplot. The matplotlib.pyplot.legend() method gives you a considerable amount of flexibility to plot interactive figures. In fact, you have three call signatures to choose from. The legend() method doesn’t even require you to explicitly pass any variables. If you call legend() with no variables then Matplotlib will automatically detect elements to add to the legend. You can also create legends using elements that already exist on the axis by calling it with legend(labels). And finally, you can pass both handles and labels with legend(handles, labels).
At this point it should be clear that the legend method is quite flexible. But that same flexibility can often lead to unexpected errors. And this is usually the underlying issue when a “no handles with labels found to put in legend” error comes up. The legend method is trying to work with data that is either absent, incorrectly formatted, or which hasn’t been correctly passed as a variable. In particular, the error is typically returned because there hasn’t been an explicit definition of a legend. With this in mind, the easiest fix is to just make sure that you’re passing the legend name with a parameter. This simple example demonstrates the point.
We’ve noted that the legend method is capable of automatically detecting some elements. That aspect of Matplotlib can be incredibly useful. But it can also lead to some easy mistakes when the underlying system isn’t quite in sync with your own intent. As such, the error message can come about as a result of a mismatch between what you think is being interpreted by legend() and what’s actually automatically created by the method. As an example, consider a case where you want to work with a bar chart.
You might begin by importing matplotlib.pyplot as plt and two NumPy arrays as x and y. Then you’d call it with something like the following.
plt.bchart(x,y ,label=’elements of label’)
In this example, you might assume that we’d see a “no handles with labels found to put in legend” error. But it’s avoided due to the fact that the autodetect in legend() was able to work with a properly defined label even if it’s not explicitly passed. The emphasis here is on the fact that it needs to be properly defined.
Some people prefer to handle all of the variables related to legend() manually in order to reduce the chance of a “no handles with labels found to put in legend” error. Consider the following example where we’ve imported pyplot as plt and plotted an arcsine, line and sine to respective variables.
plt.legend(handles = [arcsine, line, sine], labels = [‘Arcsine’, ‘Line’, ‘Sine’])
In this example, we’ve left nothing up to chance. This is a surefire way to reduce the probability of a “no handles with labels found to put in legend” error as it gives us full freedom to easily doublecheck everything that’s been passed to legend(). A more long-form methodology makes troubleshooting fairly straightforward. If the error persists then we know it’s an issue with the created line, sine, and arcsine at a point before they were passed to legend().
On top of this, there are some additional issues that might come up when using Matplotlib. For example, in some instances when you create a label prefaced with an underscore it might end up ignored by legend(). This is especially true when relying on the method’s autodetect. You don’t necessarily have to avoid using opening underscores with Matplotlib. But it’s best to use a little extra care when doing so.