user823743 - 8 months ago 64

Python Question

I have drawn a precision-recall curve using

`sklearn`

`precision_recall_curve`

`matplotlib`

`precision_recall_curve`

`sklearn`

`precision["micro"], recall["micro"], _ = precision_recall_curve(y_test.ravel(),scores.ravel())`

pr = copy.deepcopy(precision[0])

rec = copy.deepcopy(recall[0])

prInv = np.fliplr([pr])[0]

recInv = np.fliplr([rec])[0]

j = rec.shape[0]-2

while j>=0:

if prInv[j+1]>prInv[j]:

prInv[j]=prInv[j+1]

j=j-1

decreasing_max_precision = np.maximum.accumulate(prInv[::-1])[::-1]

plt.plot(recInv, decreasing_max_precision, marker= markers[mcounter], label=methodNames[countOfMethods]+': AUC={0:0.2f}'.format(average_precision[0]))

And these lines will plot the interpolated curves if you put them in a for loop and pass it the data of each method at each iteration. Note that this will not plot the non-interpolated precision-recall curves.

Answer

A backward iteration can be performed to remove the increasing parts in `precision`

. Then, vertical and horizontal lines can be plotted as specified in the answer of Bennett Brown to vertical & horizontal lines in matplotlib .

Here is a sample code:

```
import numpy as np
import matplotlib.pyplot as plt
#just a dummy sample
recall=np.linspace(0.0,1.0,num=42)
precision=np.random.rand(42)*(1.-recall)
precision2=precision.copy()
i=recall.shape[0]-2
# interpolation...
while i>=0:
if precision[i+1]>precision[i]:
precision[i]=precision[i+1]
i=i-1
# plotting...
fig, ax = plt.subplots()
for i in range(recall.shape[0]-1):
ax.plot((recall[i],recall[i]),(precision[i],precision[i+1]),'k-',label='',color='red') #vertical
ax.plot((recall[i],recall[i+1]),(precision[i+1],precision[i+1]),'k-',label='',color='red') #horizontal
ax.plot(recall,precision2,'k--',color='blue')
#ax.legend()
ax.set_xlabel("recall")
ax.set_ylabel("precision")
plt.savefig('fig.jpg')
fig.show()
```

And here is a result:

Source (Stackoverflow)