我正在尝试将所有数据文件绘制在python中的目录中,然后保存生成的图。我不试图编写高效的python代码(不幸的是):现在只对绘制数据感兴趣。
我是python的新手,我的目标是在我的论文中组织数字。
所以使用下面的代码,这就是我想要做的:
.dat
glob
个文件
plot_surface
每个数据文件我尝试绘制的数据是here
向我吐出的错误是:
File "/home/dnaneet/Research/test_collection/dftdata/profile2.py", line 59, in <module>
plot(x, y, z)
File "/usr/lib/pymodules/python2.7/matplotlib/pyplot.py", line 2286, in plot
ret = ax.plot(*args, **kwargs)
File "/usr/lib/pymodules/python2.7/matplotlib/axes.py", line 3783, in plot
for line in self._get_lines(*args, **kwargs):
File "/usr/lib/pymodules/python2.7/matplotlib/axes.py", line 317, in _grab_next_args
for seg in self._plot_args(remaining, kwargs):
File "/usr/lib/pymodules/python2.7/matplotlib/axes.py", line 278, in _plot_args
raise ValueError, 'third arg must be a format string'
ValueError: third arg must be a format string
import os import glob import sys import subprocess import matplotlib.pyplot as plt from mpl_toolkits.mplot3d import Axes3D import numpy as np from numpy import * from numpy.random import rand from pylab import pcolor, show, colorbar, xticks, yticks from pylab import * print 'Listing all profile/dat files' profilefilelist = glob.glob('*profile*.dat') raw_input('Press ENTER to continue...') print profilefilelist for i in profilefilelist: DATA = i def get_data(fname=DATA): '''Read 2d array of z coordinates from file. Convert to float values and wrap in a numpy array.''' with open(fname) as f: data = [map(float, line.split()) for line in f] return np.array(data) def plot(x, y, z): fig = plt.figure() ax = fig.gca(projection='3d') ax.plot_surface(x, y, z, rstride=5, cstride=5,cmap="binary",linewidth=0.1) ax.set_zlim3d(0.0,4.0) ax.set_xlabel('X',fontsize=16,fontweight="bold") ax.set_ylabel('Y',fontsize=16,fontweight="bold") ax.set_zlabel('h(X,T)',fontsize=16,fontweight="bold") savefig(os.getcwd()+DATA+'.pdf',figsize=(5,5),dpi=600) savefig(os.getcwd()+DATA+'.pdf',figsize=(5,5),dpi=600) if __name__ == '__main__': z = get_data() x = range(z.shape[0]) y = range(z.shape[1]) x, y = np.meshgrid(x, y) plot(x, y, z)
这是因为我的压痕不好还是在这里发生了更加险恶的事情?我该怎么做才能纠正这些错误?
我不太了解python,并一直试图摆脱mathematica(因为我将毕业,再也买不起世界上的mathematicas或matlabs)。
import os import glob import sys import subprocess import matplotlib.pyplot as plt from mpl_toolkits.mplot3d import Axes3D import numpy as np from numpy import * from numpy.random import rand from pylab import pcolor, show, colorbar, xticks, yticks from pylab import * print 'Listing all profile/dat files' profilefilelist = glob.glob('*profile*.dat') raw_input('Press ENTER to continue...') print profilefilelist DATA=profilefilelist for i in DATA: def get_data(fname=i): '''Read 2d array of z coordinates from file. Convert to float values and wrap in a numpy array.''' with open(fname) as f: data = [map(float, line.split()) for line in f] return np.array(data) for i in DATA: def my_plot(x, y, z): fig = plt.figure() ax = fig.gca(projection='3d') ax.plot_surface(x, y, z, rstride=5, cstride=5,cmap="binary",linewidth=0.1) ax.set_zlim3d(0.0,4.0) ax.set_xlabel('X',fontsize=16,fontweight="bold") ax.set_ylabel('Y',fontsize=16,fontweight="bold") ax.set_zlabel('h(X,T)',fontsize=16,fontweight="bold") plt.show() # savefig(os.getcwd()+DATA+'.pdf',figsize=(5,5),dpi=600) # savefig(os.getcwd()+DATA+'.pdf',figsize=(5,5),dpi=600) if __name__ == '__main__': z = get_data() x = range(z.shape[0]) y = range(z.shape[1]) x, y = np.meshgrid(x, y) my_plot(x, y, z)
答案 0 :(得分:2)
至少有一个缩进问题我可以看到(虽然我没有所有的依赖关系来重现这个)。
您的def图(x,y,z)位于def get_data函数内(位于for循环内)。
你只需要定义一次你的函数,这样你就可以将def get_data和def绘制线从第0列开始。然后你的
if __name__ == '__main__'
块将调用您的绘图函数而不是pyplot(如回溯中所示)。
同样,您只需要使用您正在寻找的DATA文件调用它,而不是在for循环中定义get_data。
答案 1 :(得分:2)
一些清理建议(你的任务很简单,我认为有一些不必要的操作):
raw_input
仅用于确认等)from module import *
,因为它已导致名称冲突。以下是您的程序的修改版本,我相信它可以实现相同的结果。它不是您的问题的解决方案,而是一系列小改进(或我认为是改进):
import os
import glob
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
import numpy as np
for fname in glob.glob('*profile*.dat'):
z = numpy.loadtxt(fname)
x,y = np.meshgrid(range(z.shape[0]), range(z.shape[1]))
fig = plt.figure()
ax = fig.gca(projection='3d')
ax.plot_surface(x, y, z, rstride=5, cstride=5,cmap="binary",linewidth=0.1)
ax.set_zlim3d(0.0,4.0)
ax.set_xlabel('X',fontsize=16,fontweight="bold")
ax.set_ylabel('Y',fontsize=16,fontweight="bold")
ax.set_zlabel('h(X,T)',fontsize=16,fontweight="bold")
plt.savefig(os.getcwd()+fname+'.pdf',figsize=(5,5),dpi=600)
plt.savefig(os.getcwd()+fname+'.pdf',figsize=(5,5),dpi=600)
您可以选择使用最后两行:
plt.savefig(os.path.join(os.getcwd, "%s.pdf" % fname), figsize=(5,5), dpi=600)
答案 2 :(得分:1)
您已经定义了自己的函数并将其命名为plot
,但是当您调用plot(x,y,z)
时,它看起来正在调用标准pyplot.plot
命令(请参阅回溯中的代码位置) )。请尝试将其重命名为my_plot
。
一般而言,在这种情况下,强烈建议不要使用其他常用函数的名称来命名自己的对象(函数和变量)。
正如@tstone所说,你的函数定义在循环内部,在运行循环之前定义它们,但也给它们唯一的名称。使用唯一名称,如果您愿意,您仍然可以使用普通的plot
函数,并且您已经捕获了作用域错误(它在循环中定义)因为唯一名称({{ 1}},例如)本来是未定义的。
尝试重构您的脚本:
my_plot
请注意,我更改了import ...
def get_data(fname): #fname is now a required argument, to be fed in by the loop in __main__ body
'''Read 2d array of z coordinates from file. Convert to float values
and wrap in a numpy array.'''
...
# should pass DATA to the savefig:
def my_plot(x, y, z, DATA):
...
savefig(...DATA...)
# do everything else here:
if __name__ == '__main__':
print 'Listing all profile/dat files'
profilefilelist = glob.glob('*profile*.dat')
raw_input('Press ENTER to continue...')
print profilefilelist
# you didn't need `i` since you just immediately assigned it to DATA, just call it DATA in the first place
for DATA in profilefilelist:
z = get_data(DATA)
x = range(z.shape[0])
y = range(z.shape[1])
x, y = np.meshgrid(x, y)
my_plot(x, y, z, DATA) # Here, pass DATA to `my_plot`
的参数,以便它没有默认参数,但它会接受一个变量(此处称为get_data
来自循环)。
答案 3 :(得分:1)
一个简单的例子,可以帮助您了解函数和循环的工作原理。
# Here I define bar 10 times, but call it 1 times
# This is what you're doing in your code
print "defining bar 10 times"
for i in range(10):
def bar(i):
print "bar " + str(i)
print "running it once"
bar(99)
# Here I define foo once, and call it 10 times
# This is what I think you're trying to do
print "defining foo once"
def foo(i):
print "foo " + str(i)
print "running foo 10 times"
for i in range(10):
foo(i)
这是上述代码的输出:
defining bar 10 times
running it once
bar 99
defining foo once
running foo 10 times
foo 0
foo 1
foo 2
foo 3
foo 4
foo 5
foo 6
foo 7
foo 8
foo 9