1

我对 Python 很陌生,我正在尝试编写一个程序,该程序将执行 4 点线性插值,从 .txt 文件读取数据并询问用户信息。

.txt 文件在具有以下格式的表格中包含温度和压力:

T    P1  P2  P3  P4
     80,100,150,200
75,  400,405,415,430
100, 450,456,467,483
150, 500,507,519,536
200, 550,558,571,589

这是代码:

# User input
temp = input("Enter temperature value in degrees Celcius [Range: 75-200]:")
pressure = input("Enter pressure value in bars [Range: 80-589")

temp = float(temp)
pressure = float(pressure)

# Opens file and read data
filename = open('xxxxxxxxxxxxx.txt', 'r').readlines()

# Removes \n from each line
for i in list(range((len(filename)-1))):
    filename[i] = filename[i][:-1]

# Splits string
for i in list(range(len(filename))):
    filename[i] = filename[i].split(',')

# Converts string numbers into decimal numbers
for i in [2,3,4,5,6]:
    filename[i][0] = float(filename[i][0])
    filename[i][1] = float(filename[i][1])

我不知道从这里去哪里。如果用户输入说,T=100 和 P=200,我将如何从文件中找到直接在这些数字之前和之后的数据点?

显然,我不太了解我在做什么,但我会很感激任何帮助。

ETA:实际表值。另外,我不清楚实际的问题陈述。给定温度和压力,程序应执行线性插值以找到 U(内能)。T 值是第一列,P 值是第一行,其余的是 U 值。

4

3 回答 3

2

这里有两个单独的问题:如何将数据读入 python/NumPy,以及如何进行 2d 插值。
对于读取数据,我建议 使用 numpy loadtxt
对于插值, 建议使用 scipy BivariateSpline。(他们都有比你需要的更多的选择。)

from __future__ import division
from cStringIO import StringIO
import numpy as np
from scipy.interpolate import RectBivariateSpline

np.set_printoptions( 1, threshold=100, edgeitems=10, suppress=True )

    # a file inline, for testing --
myfile = StringIO( """
# T  P1  P2  P3  P4
0,   80,100,150,200

75,  400,405,415,430
100, 450,456,467,483
150, 500,507,519,536
200, 550,558,571,589
""" )

    # file -> numpy array --
    # (all rows must have the same number of columns)
TPU = np.loadtxt( myfile, delimiter="," )
P = TPU[0,1:]  # top row
T = TPU[ 1:,0]  # left col
U = TPU[1:,1:]  # 4 x 4, 400 .. 589
print "T:", T
print "P:", P
print "U:", U

interpolator = RectBivariateSpline( T, P, U, kx=1, ky=1 )  # 1 bilinear, 3 spline

    # try some t, p --
for t, p in (
    (75, 80),
    (75, 200),
    (87.5, 90),
    (200, 80),
    (200, 90),
    ):
    u = interpolator( t, p )
    print "t %5.1f  p %5.1f -> u %5.1f" % (t, p, u)

顺便说一句,对于交互式 python, IPython 可以很容易地尝试单行,查看变量......

于 2012-05-05T16:33:09.023 回答
1

假设您有一个排序的数字列表x1, x2, x3... xn,您可以使用该bisect模块快速定位您想要的间隔(O(log n))。

from bisect import bisect, bisect_right, bisect_left
#    0    1    2    3    4    5    6    7
x = [1,   2,   4,   8,  16, 100, 200, 300]


def find_interval(x,y):
    # x must be a sorted list.

    index = bisect_left(x,y)
    # Larger than largest element in x
    if index >= len(x):
        l,r = -1, None
    # Exactly equal to something in x
    elif y == x[index]:
        l,r = index, index
    # Smaller than smallest element in x
    elif index == 0:
        l,r = None, 0
    # Inbetween two elements in x
    else:
        l,r = index-1, index

    print (x[l] if l != None else "To left of all elements")
    print (x[r] if r != None else "To right of all elements")
    return (l,r)

>>> x
[1, 2, 4, 8, 16, 100, 200, 300]
>>> find_interval(x,0)
To left of all elements
1
>>> find_interval(x,1000)
300
To right of all elements
>>> find_interval(x,100)
100
100
>>> find_interval(x,12)
8
16
>>> 
于 2012-05-03T05:54:47.833 回答
0
  1. .readlines()一旦文件变大,使用就会让你大吃一惊。你能根据以下方面制定你需要做的事情吗?

    for line in open(...):
        # parse line
    

    并只解析一次文件而不将其完全加载到内存中。

    • 更好的是,with在处理文件时使用成语:

      with open(...) as file:
          for line in file:
              # parse line
      

      当使用文件时出现问题时,这可以为您省去一些麻烦。

  2. float()如果您最终要使用从字符串中制作浮点数,则不需要删除换行符。float('1.2 \t\n')是完全有效的代码。

  3. for i in list(range(len(filename))):

    这是不好的风格。遍历列表的 Python 习惯用法是

    for element in list:
    

    如果您需要列表中的索引,那么您应该使用

    for i, element in enumerate(list):
    

    您的方法是一种“手动”并且它有效,但是完全没有必要从lista 中创建一个list(来自python 2.x)。range(...)您的代码的更好的“手动”替代方案是

    for i in xrange(len(filename)):
    

    但它仍然比上面的习语可读性差得多。

现在我已经完成了对您的代码的抨击,主要问题是:您实际上需要做什么?你能给我们准确的、逐字的、你试图解决的问题的说明吗?

  • 你看过http://en.wikipedia.org/wiki/Linear_interpolation吗?
  • 在您的情况下,来自终端的输入数据有什么意义?
  • 为什么以及为什么需要来自终端输入数据之前和之后的文件中的数据?
  • 温度/压力数据是否以某种方式排序?
  • 文件中的行代表什么(例如,它们是基于时间的还是基于位置的或其他)?
  • 四种不同的压力分别代表什么?
于 2012-05-03T04:52:12.180 回答