[英]Trying to interpolate linearly in python
I have 3 arrays: a, b, c all with length 15. 我有3个数组:a,b,c的长度均为15。
a=[950, 850, 750, 675, 600, 525, 460, 400, 350, 300, 250, 225, 200, 175, 150]
b = [16, 12, 9, -35, -40, -40, -40, -45, -50, -55, -60, -65, -70, -75, -80]
c=[32.0, 22.2, 12.399999999999999, 2.599999999999998, -7.200000000000003, -17.0, -26.800000000000004, -36.60000000000001, -46.400000000000006, -56.2, -66.0, -75.80000000000001, -85.60000000000001, -95.4, -105.20000000000002]
I am trying to find the value of a at the index where b=c. 我正在尝试在b = c的索引处找到a的值。 T
Ť
The problem is that there is no place where b=c exactly so I need to linearly interpolate between values in the array to find the value of a where b=c. 问题在于,b = c完全没有位置,因此我需要在数组中的值之间线性插值以找到a的值,其中b = c。 Does that make sense?
那有意义吗?
I was thinking about using scipy.interpolate to do the interpolation. 我正在考虑使用scipy.interpolate进行插值。
I am having a hard time wrappying my mind around how to solve this problem. 我很难解决如何解决这个问题。 Any ideas on this would be great!
任何想法都很棒!
Here's simpler variation of a function from another answer of mine : 这是我的另一个答案中函数的简单变化:
from __future__ import division
import numpy as np
def find_roots(t, y):
"""
Given the input signal `y` with samples at times `t`,
find the times where `y` is 0.
`t` and `y` must be 1-D numpy arrays.
Linear interpolation is used to estimate the time `t` between
samples at which sign changes in `y` occur.
"""
# Find where y crosses 0.
transition_indices = np.where(np.sign(y[1:]) != np.sign(y[:-1]))[0]
# Linearly interpolate the time values where the transition occurs.
t0 = t[transition_indices]
t1 = t[transition_indices + 1]
y0 = y[transition_indices]
y1 = y[transition_indices + 1]
slope = (y1 - y0) / (t1 - t0)
transition_times = t0 - y0/slope
return transition_times
That function can be used with t = a
and y = b - c
. 该函数可以与
t = a
和y = b - c
。 For example, here is your data, entered as numpy arrays: 例如,这是您的数据,以numpy数组形式输入:
In [354]: a = np.array([950, 850, 750, 675, 600, 525, 460, 400, 350, 300, 250, 225, 200, 175, 150])
In [355]: b = np.array([16, 12, 9, -35, -40, -40, -40, -45, -50, -55, -60, -65, -70, -75, -80])
In [356]: c = np.array([32.0, 22.2, 12.399999999999999, 2.599999999999998, -7.200000000000003, -17.0, -26.800000000000004, -3
...: 6.60000000000001, -46.400000000000006, -56.2, -66.0, -75.80000000000001, -85.60000000000001, -95.4, -105.2000000000
...: 0002])
The place where "b = c" is the place where "b - c = 0", so we pass b - c
for y
: “ b = c”的地方就是“ b-c = 0”的地方,因此我们将
b - c
传递给y
:
In [357]: find_roots(a, b - c)
Out[357]: array([ 312.5])
So the linearly interpolated value of a
is 312.5. 因此,
a
的线性内插值为312.5。
With the following matplotlib commands: 使用以下matplotlib命令:
In [391]: plot(a, b, label="b")
Out[391]: [<matplotlib.lines.Line2D at 0x11eac8780>]
In [392]: plot(a, c, label="c")
Out[392]: [<matplotlib.lines.Line2D at 0x11f23aef0>]
In [393]: roots = find_roots(a, b - c)
In [394]: [axvline(root, color='k', alpha=0.2) for root in roots]
Out[394]: [<matplotlib.lines.Line2D at 0x11f258208>]
In [395]: grid()
In [396]: legend(loc="best")
Out[396]: <matplotlib.legend.Legend at 0x11f260ba8>
In [397]: xlabel("a")
Out[397]: <matplotlib.text.Text at 0x11e71c470>
I get the plot 我知道了
This is not necessarily a solution to your problem, since your data does not appear to be linear, but it might give you some ideas. 这不一定解决您的问题,因为您的数据似乎不是线性的,但可能会给您一些想法。 If you assume that your lines a, b, and c are linear, then the following idea works:
如果假设您的线a,b和c是线性的,则以下想法可行:
Perform a linear regression of lines a, b and c to get their respective slopes (m_a, m_b, m_c) and y-intercepts (b_a, b_b, b_c). 对线a,b和c进行线性回归以获得其各自的斜率(m_a,m_b,m_c)和y截距(b_a,b_b,b_c)。 Then solve the equation 'y_b = y_c' for x, and find y = m_a * x + b_a to get your result.
然后为x求解方程'y_b = y_c',找到y = m_a * x + b_a以得到结果。
Since the linear regression approximately solves y = m * x + b, equation y_b = y_c can be solved by hand giving: x = (b_b-b_c) / (m_c-m_b). 由于线性回归近似求解y = m * x + b,因此方程y_b = y_c可以手工给出:x =(b_b-b_c)/(m_c-m_b)来求解。
Using python, you get: 使用python,您将获得:
>> m_a, b_a, r_a, p_a, err_a = stats.linregress(range(15), a)
>> m_b, b_b, r_b, p_b, err_b = stats.linregress(range(15), b)
>> m_c, b_c, r_c, p_c, err_c = stats.linregress(range(15), c)
>> x = (b_b-b_c) / (m_c-m_b)
>> m_a * x + b_a
379.55151515151516
Since your data is not linear, you probably need to go through your vectors one by one and search for overlapping y intervals. 由于数据不是线性的,因此您可能需要一个一个地遍历向量并搜索重叠的y间隔。 Then you can apply the above method but using only the endpoints of your two intervals to construct your b and c inputs to the linear regression.
然后,您可以应用上述方法,但仅使用两个间隔的端点来构造线性回归的b和c输入。 In this case, you should get an exact result, since the least-squares method will interpolate perfectly with only two points (although there are more efficient ways to do this since the intersection can be solved exactly in this simple case where there are two straight lines).
在这种情况下,您应该得到一个精确的结果,因为最小二乘法将仅用两个点完美地进行插值(尽管存在更有效的方法,因为在这种简单的情况下,只要有两个直线线)。
Cheers. 干杯。
Another simple solution using: 另一个简单的解决方案是:
a=[950, 850, 750, 675, 600, 525, 460, 400, 350, 300, 250, 225, 200, 175, 150]
b = [16, 12, 9, -35, -40, -40, -40, -45, -50, -55, -60, -65, -70, -75, -80]
c=[32.0, 22.2, 12.399999999999999, 2.599999999999998, -7.200000000000003, -17.0, -26.800000000000004, -36.60000000000001, -46.400000000000006, -56.2, -66.0, -75.80000000000001, -85.60000000000001, -95.4, -105.20000000000002]
from sklearn.linear_model import LinearRegression
from scipy.optimize import minimize
import numpy as np
reg_a = LinearRegression().fit(np.arange(len(a)).reshape(-1,1), a)
reg_b = LinearRegression().fit(np.arange(len(b)).reshape(-1,1), b)
reg_c = LinearRegression().fit(np.arange(len(c)).reshape(-1,1), c)
funA = lambda x: reg_a.predict(x.reshape(-1,1))
funB = lambda x: reg_b.predict(x.reshape(-1,1))
funC = lambda x: reg_c.predict(x.reshape(-1,1))
opt_crossing = lambda x: (funB(x) - funC(x))**2
x0 = 1
res = minimize(opt_crossing, x0, method='SLSQP', tol=1e-6)
print(res)
print('Solution: ', funA(res.x))
import matplotlib.pyplot as plt
x = np.linspace(0, 15, 100)
a_ = reg_a.predict(x.reshape(-1,1))
b_ = reg_b.predict(x.reshape(-1,1))
c_ = reg_c.predict(x.reshape(-1,1))
plt.plot(x, a_, color='blue')
plt.plot(x, b_, color='green')
plt.plot(x, c_, color='cyan')
plt.scatter(np.arange(15), a, color='blue')
plt.scatter(np.arange(15), b, color='green')
plt.scatter(np.arange(15), c, color='cyan')
plt.axvline(res.x, color='red', linestyle='solid')
plt.axhline(funA(res.x), color='red', linestyle='solid')
plt.show()
fun: array([ 7.17320622e-15])
jac: array([ -3.99479864e-07, 0.00000000e+00])
message: 'Optimization terminated successfully.'
nfev: 8
nit: 2
njev: 2
status: 0
success: True
x: array([ 8.37754008])
Solution: [ 379.55151658]
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.