Excel UDF使用第五多项式从给定的X值返回Y值

Excel UDF使用第五多项式从给定的X值返回Y值,excel,vba,user-defined-functions,polynomials,Excel,Vba,User Defined Functions,Polynomials,我在同一工作簿中的多个工作表上有一个范围,一列中有35个“X”值,需要返回“Y”值,对应于名为“DB”的固定工作表上的自定义第五多项式曲线/函数,支持C37:C76上的“X”值和D37:D76上上述曲线的“Y”值 本质上是一个图形化的VLOOKUP函数,而不是一个有1000行的表 作为一次性计算,正常计算方法可以100%工作,但如果需要在多张图纸上计算X的多个值的Y,则会成为一个问题。我原以为UDF会起作用,但我真的不知道该怎么做。我尝试了一些代码变体,并从这篇文章开始整理 我们将非常感谢您对本

我在同一工作簿中的多个工作表上有一个范围,一列中有35个“X”值,需要返回“Y”值,对应于名为“DB”的固定工作表上的自定义第五多项式曲线/函数,支持C37:C76上的“X”值和D37:D76上上述曲线的“Y”值

本质上是一个图形化的VLOOKUP函数,而不是一个有1000行的表

作为一次性计算,正常计算方法可以100%工作,但如果需要在多张图纸上计算X的多个值的Y,则会成为一个问题。我原以为UDF会起作用,但我真的不知道该怎么做。我尝试了一些代码变体,并从这篇文章开始整理

我们将非常感谢您对本UDF的任何帮助

Function ADJ(X As Single) As Single

'X = FUNCTION INPUT VALUE
'Y = RESULT = ADJ = C5*X^5 + C4*X^4 + C3*X^3 + C2*X^2 + C1*X^1 + A
        
        C1 = Sheets(11).Evaluate("=INDEX(LINEST(R37C3:R76C3, R37C4:R76C4^{1,2,3,4,5}), 1, 5)")
        C2 = Sheets(11).Evaluate("=INDEX(LINEST(R37C3:R76C3, R37C4:R76C4^{1,2,3,4,5}), 1, 4)")
        C3 = Sheets(11).Evaluate("=INDEX(LINEST(R37C3:R76C3, R37C4:R76C4^{1,2,3,4,5}), 1, 3)")
        C4 = Sheets(11).Evaluate("=INDEX(LINEST(R37C3:R76C3, R37C4:R76C4^{1,2,3,4,5}), 1, 2)")
        C5 = Sheets(11).Evaluate("=INDEX(LINEST(R37C3:R76C3, R37C4:R76C4^{1,2,3,4,5}), 1, 1)")
         A = Sheets(11).Evaluate("=INDEX(LINEST(R37C3:R76C3, R37C4:R76C4^{1,2,3,4,5}), 1, 6)")
       ADJ = C5 * X ^ 5 + C4 * X ^ 4 + C3 * X ^ 3 + C2 * X ^ 2 + C1 * X ^ 1 + A
         
End Function

将其作为子系统运行:

Option Explicit

Sub ADJ1()

Dim ADJ As Variant
Dim X As Variant
Dim A As Variant
Dim C1 As Variant
Dim C2 As Variant
Dim C3 As Variant
Dim C4 As Variant
Dim C5 As Variant

X = 3

         C1 = Sheets(11).Evaluate("=INDEX(LINEST(D37:D76, C37:C76^{1,2,3,4,5}), 1, 5)")
         C2 = Sheets(11).Evaluate("=INDEX(LINEST(D37:D76, C37:C76^{1,2,3,4,5}), 1, 4)")
         C3 = Sheets(11).Evaluate("=INDEX(LINEST(D37:D76, C37:C76^{1,2,3,4,5}), 1, 3)")
         C4 = Sheets(11).Evaluate("=INDEX(LINEST(D37:D76, C37:C76^{1,2,3,4,5}), 1, 2)")
         C5 = Sheets(11).Evaluate("=INDEX(LINEST(D37:D76, C37:C76^{1,2,3,4,5}), 1, 1)")
          A = Sheets(11).Evaluate("=INDEX(LINEST(D37:D76, C37:C76^{1,2,3,4,5}), 1, 6)")
       
       'ADJ = C5 * X ^ 5 + C4 * X ^ 4 + C3 * X ^ 3 + C2 * X ^ 2 + C1 * X ^ 1 + A
       
       ADJ = X ^ 5 + X ^ 4 + X ^ 3 + X ^ 2 + X ^ 1
       MsgBox ADJ
       
       
End Sub

我有一个解决方案和意见。我仍然不确定这个观点是否正确。 意见:我决不会将UDF用于范围。使用的范围必须是函数的参数。 请参阅此解决方案:

Public Function ADJ(X As Range, Y As Range, xvalue As Double) As Double
    Dim pol As Variant
    Dim arrPolNth As Variant
    Dim n As Integer
    n = 5
    arrPolNth = Array(1, 2, 3, 4, 5)
    pol = Application.LinEst(Y, Application.Power(X, arrPolNth))
    Dim i As Integer
    For i = LBound(pol) To UBound(pol)
        ADJ = ADJ + Application.Power(xvalue, n - i + 1) * pol(i)
    Next i
End Function

它不是最好的,因为多项式的顺序也应该是一个参数。

如果要计算工作表公式,则需要使用
工作表。计算方法。例如
C1=mySheet.Evaluate(“=INDEX(LINEST(R37C3:R76C3,R37C4:R76C4^{1,2,3,4,5}),1,5)”
并在分配到该行的输入后将
ADJ=…
行移动到。谢谢Tim,我更新了代码(如上所示),但得到了一个#值!Error从子系统运行函数,以便查看问题所在。你真的有一个代号为“mySheet”的工作表吗?我给了X一个随机值,没有任何C1到a的值,它就工作了,即弹出一个带有计算出的调整值的消息框。例如,当我添加一个实例时,我得到一个类型不匹配错误。我猜这意味着A计算会返回一个错误。。也许?可能是因为
表单(11).Evaluate(=索引(LINEST(D37:D76,C37:C76^{1,2,3,4,5}),1,6)”
格式不正确吗?谢谢Viktor。有趣的解决方案。我考虑使用一个范围,因为这样我可以绘制曲线并微调它以适应一个中心位置。如果我理解正确,那么范围应该是VBA代码的一部分,而不是位于图纸上?如果是这样,我应该在哪里定义X和Y的值(每个值40个)?实际上,如果从工作表中调用函数,那么与范围对象直接通信不是一个好的做法。如果希望使用数组(范围)而不是单个值,则函数应具有输入范围,并可返回计算估计值的数组。如果您对这个解决方案满意,我可以为您修改代码。啊,现在我知道您在那里做了什么。我忽略了一个事实,即范围是在UDF中定义的,即
=ADJ(D37:D76,C37:C76,H51)
(即使您这样说),现在它可以完美地工作,就像您在上面建议的那样!非常感谢你,维克多!