Closed MES-physics closed 1 year ago
If you have force data in your xyz file and read by ase, the force info is stored in 'atoms.arrays['force']'. So you should try to use f2.append(i.arrays['force'].reshape(-1))
Thanks, but no, now it's the same error with this key.
f2.append(i.info['force'].reshape(-1)) KeyError: 'force'
Can you please look into it further? What else could I do ? Thanks
I didn't generate the data with ase, my xyz file has "forces".
You can try to read your xyz data by pynep instead of ase:
from pynep.io import load_nep
frames =load_nep('xxx.xyz', ftype="exyz")
and test print(frames[0].info['forces'])
Yes, success now with plotting! thanks! But now the forces plot does not show the RMSE?
Here is that part of the code:
def plot_f(fd, fr):
fig = plt.figure()
ax = plt.gca()
plt.title("NEP forces vs DFT forces", fontsize=16)
ax.set_aspect(1)
xmajorLocator = ticker.MaxNLocator(5)
ymajorLocator = ticker.MaxNLocator(5)
ax.xaxis.set_major_locator(xmajorLocator)
ax.yaxis.set_major_locator(ymajorLocator)
ymajorFormatter = ticker.FormatStrFormatter('%.1f')
xmajorFormatter = ticker.FormatStrFormatter('%.1f')
ax.xaxis.set_major_formatter(xmajorFormatter)
ax.yaxis.set_major_formatter(ymajorFormatter)
ax.set_xlabel('DFT forces (eV/A)', fontsize=14)
ax.set_ylabel('NEP forces (eV/A)', fontsize=14)
ax.spines['bottom'].set_linewidth(2)
ax.spines['left'].set_linewidth(2)
ax.spines['right'].set_linewidth(2)
ax.spines['top'].set_linewidth(2)
ax.tick_params(labelsize=14)
ax.set_xlim(np.min(fd), np.max(fd))
ax.set_ylim(np.min(fr), np.max(fr))
plt.plot([np.min(fd), np.max(fd)], [np.min(fr), np.max(fr)],
color='black',linewidth=2,linestyle='--')
plt.scatter(fd.reshape(-1), fr.reshape(-1), s=2)
m1 = min(np.min(fd), np.min(fr))
m2 = max(np.max(fd), np.max(fr))
# ax.set_xlim(m1, m2)
# ax.set_ylim(m1, m2)
ax.set_xlim(-100, 100)
ax.set_ylim(-100, 100)
rmse = np.sqrt(np.mean((fd-fr)**2))
plt.text(np.min(fd) * 0.85 + np.max(fd) * 0.15,
np.min(fr) * 0.15 + np.max(fr) * 0.85,
"RMSE: {:.3f} eV/A".format(rmse), fontsize=14)
plt.savefig('f.png')
plt.show()
return fig
But printing the number works after the rmse= ...
definition.
rmse = np.sqrt(np.mean((fd-fr)**2))
print(rmse) #works
It just does not print on the plot.
I found out more. RMSE does print on the plot with the original full axis limits. When I put different axis limits, it won't print on the plot. How to fix this? Thanks.
You can try plt.text("RMSE: {:.3f} eV/A".format(rmse), fontsize=14)
. This may determine the best loction to show the text.
I got back to this now.
plt.text("RMSE: {:.3f} eV/A".format(rmse), fontsize=14)
TypeError: text() missing 2 required positional arguments: 'y' and 's'
What should y and s be? How to define them in the code you posted? I tried defining them as "top" and "left" , but it said it can't convert to axis units.
Thanks
Hi again, I tried to run plot_calcefs.py with my NEP datafiles, and the following error occurs:
f2.append(i.info['forces'].reshape(-1)) KeyError: 'forces'
Can you enlighten me please? My files are normal from doing NEP training, input a .xyz training file, and output, a nep.txt file.