I produced data for a curve, stored in a list. Then I took 1000 random samples out of that data. The y-axis shows my data and the x-axis I the formula output. Up till here everything is fine. The problem starts when I want to plot my data onto an existing image.
As you can see, my x-axis and y-axis are log scale and lower than 1. I have looked for answers and found that I could use FuncFormatter. However, it doesn't work for me, as I need to plot my data with log-scale. When I use simply plt.xscale('log')
the figure looks like this:
Output figure with log-scale
Output figure without log-scale
import matplotlib.pyplot as plt
import numpy as np
#Producing some data and put them in a list named listGercek
xekseni2 = []
data = random.sample(listGercek, 1000)
for teta in data:
olasılık = listGercek.index(teta)/100000
xekseni2.append(olasılık)
im = plt.imread('figure.png')
xmin, xmax, ymin, ymax = (0.001, 1, 0.01, 1)
aspect = im.shape[0] / im.shape[1] * (xmax-xmin)/(ymax-ymin)
plt.imshow(im, zorder=0, extent=[1e-3, 1e0, 1e-2, 1e0], aspect=aspect)
plt.yscale('log')
plt.xscale('log')
plt.xlabel('P')
plt.ylabel(r'$\tau_{c}^{*}$')
plt.plot(xekseni2, data, "ro", marker="o", markersize=1, label="Present Work")
plt.axis([xmin, xmax, ymin, ymax])
plt.legend()
plt.show()
Some data points as asked:
y:0.09141346037829952, 0.06969760102294438, 0.0473781028644485, 0.059295628198887916, 0.0571418702849134, 0.04050307759274645, 0.08088991113201109, 0.03746878506083184, 0.13583224333004337, 0.03269066677698429, 0.06918929672995293, 0.06040315211901601, 0.05772815718352134, 0.07361582566248871, 0.06212973486945907, 0.03283216378016191, 0.14407484921136313, 0.02266323793619761, 0.04439409523587426, 0.055067724315696655,
x:0.81136, 0.67958, 0.43465, 0.58106, 0.55695, 0.33327, 0.75665, 0.2849, 0.93146, 0.20716, 0.6752, 0.59276, 0.56391, 0.70997, 0.6097, 0.20941, 0.94315, 0.06609, 0.39222, 0.53361,
The problem is that changing to log scale axes, the image also gets deformed. So, the image needs a linear scale.
One approach is to draw the image on a secondary x and y axis, with linear scale. And to draw the curve on the original axes with double log scale.
The primary axes get a zorder
to be in front of the secondary axes. So the new curve comes on top of everything. To make the image visible, the facecolor of the primary axes need to be transparent (color string 'none' instead of the default 'white').
To hide the secondary axis, also the intermediate twinx()
needs to be hidden. (See the remarks under this post.)
To get the aspect ratio correct, only aspect='auto'
seems to work as desired, setting the limits the same for both the primary and secondary axes.
import matplotlib.pyplot as plt
import numpy as np
xekseni2 = [0.81136, 0.67958, 0.43465, 0.58106, 0.55695, 0.33327, 0.75665, 0.2849, 0.93146, 0.20716, 0.6752, 0.59276,
0.56391, 0.70997, 0.6097, 0.20941, 0.94315, 0.06609, 0.39222, 0.53361]
data = [0.09141346037829952, 0.06969760102294438, 0.0473781028644485, 0.059295628198887916, 0.0571418702849134,
0.04050307759274645, 0.08088991113201109, 0.03746878506083184, 0.13583224333004337, 0.03269066677698429,
0.06918929672995293, 0.06040315211901601, 0.05772815718352134, 0.07361582566248871, 0.06212973486945907,
0.03283216378016191, 0.14407484921136313, 0.02266323793619761, 0.04439409523587426, 0.055067724315696655]
xmin, xmax, ymin, ymax = (0.001, 1, 0.01, 1)
ax = plt.gca()
ax.plot(xekseni2, data, "ro", marker="o", markersize=1, label="Present Work")
ax.set_yscale('log')
ax.set_xscale('log')
ax.set_xlabel('P')
ax.set_ylabel(r'$\tau_{c}^{*}$')
ax.set_xlim(xmin, xmax)
ax.set_ylim(ymin, ymax)
ax.legend(loc='lower right')
ax.set_zorder(2)
ax.set_facecolor('none')
ax_tw_x = ax.twinx()
ax_tw_x.axis('off')
ax2 = ax_tw_x.twiny()
im = plt.imread('figure.png')
ax2.imshow(im, extent=[xmin, xmax, ymin, ymax], aspect='auto')
ax2.axis('off')
plt.show()
PS: Another approach could be to draw everything on the same axes but convert the curve coordinates manually to log space. The axes then are linear for both the image as well as the curve. The visual aspect of the axes could be adapted to mimic log axes, as explored in this post.