Excel 2013 VBA按等级排序

Excel 2013 VBA按等级排序,vba,sorting,excel,Vba,Sorting,Excel,问题是: 我需要插入输入到模板的值。听起来很简单,对吧?问题是,这些值并不总是按数字顺序排列,所以它会弄乱我的插值函数。我的插值函数有一个输入x值(在本例中为HP,这是需要进行数字排序而不会弄乱相关数据的参数)、y值(希望在?HP处找到的参数)和希望在其中找到y参数的x_值。有些y参数是方程,所以我想不出一种方法来完全重新排序列,而不会弄乱数据。我认为应该有一种方法来引用集合中HP的排名,选择相关的y值,并使用这些值进行插值。尽管如此,我似乎不知道该怎么做。我已经在编写一些代码很长一段时间了。我

问题是:

我需要插入输入到模板的值。听起来很简单,对吧?问题是,这些值并不总是按数字顺序排列,所以它会弄乱我的插值函数。我的插值函数有一个输入x值(在本例中为HP,这是需要进行数字排序而不会弄乱相关数据的参数)、y值(希望在?HP处找到的参数)和希望在其中找到y参数的x_值。有些y参数是方程,所以我想不出一种方法来完全重新排序列,而不会弄乱数据。我认为应该有一种方法来引用集合中HP的排名,选择相关的y值,并使用这些值进行插值。尽管如此,我似乎不知道该怎么做。我已经在编写一些代码很长一段时间了。我以前从未真正使用过VBA,所以它一直在帮我赚钱。到目前为止,我的守则如下:

Function organize(ByVal x As Object)

' Declarations for finding Ranks
Dim Array_Size As Integer
Array_Size = Application.WorksheetFunction.Count(x.cells) + Application.WorksheetFunction.CountBlank(x.cells)

Dim Ranks As Variant
ReDim Ranks(1 To Array_Size)
Dim j As Integer  'initiate counter

For j = 1 To Array_Size

    If x.cells(j).Value <> 0 Then

        Ranks(j) = Application.WorksheetFunction.Rank_Eq(x.cells(i).Value, x.cells, 1) 'assign rank to i'th position in array

    End If

Next j

organize = Ranks()


End Function


Function lin_2xy(ByVal x1 As Single, ByVal y1 As Single, _
                 ByVal x2 As Single, ByVal y2 As Single, _
                 ByVal x_value As Single)

If x1 = x2 Then
   lin_2xy = [#N/A]
Else
   lin_2xy = y1 + (y2 - y1) / (x2 - x1) * (x_value - x1)
End If

End Function


Function Sort_Then_Interpolate(ByVal x As Object, ByVal y As Object, ByVal x_value As Single)

'Declarations for interpolating
Dim i As Integer                ' counter.
Dim Current_x As Single       ' x value
Dim Next_x As Single          ' next higher x value
Dim Current_y As Single        ' y value
Dim Next_y As Single           ' next higher y value
Dim LFound As Boolean           ' = true if found.
Dim matrix() As Variant

matrix = organize(x.cells)

LFound = False

For i = 1 To UBound(matrix)

match_value = Application.WorksheetFunction.Match(i, matrix, 0)
next_match = Application.WorksheetFunction.Match(i + 1, matrix, 0)

Current_x = x.cells(match_value).Value
Next_x = x.cells(next_match).Value
Current_y = y.cells(match_value).Value
Next_y = y.cells(next_match).Value

   If ((Current_x - x_value) * (Next_x - x_value) <= 0#) Then
      Sort_Then_Interpolate = lin_2xy(Current_x, Current_y, Next_x, Next_y, x_value)
      LFound = True

   End If
Next i

If (LFound = False) Then Sort_Then_Interpolate = [#N/A]

End Function
函数组织(ByVal x作为对象)
"排名宣言",
Dim数组\u大小为整数
数组大小=Application.WorksheetFunction.Count(x.cells)+Application.WorksheetFunction.CountBlank(x.cells)
Dim作为变体排列
ReDim列组(1到阵列大小)
作为整数的Dim j启动计数器
对于j=1到数组大小
如果x.cells(j).值为0,则
秩(j)=应用程序.工作表函数.秩_Eq(x.cells(i).值,x.cells,1)'将秩分配到数组中的第i个位置
如果结束
下一个j
组织=等级()
端函数
函数lin_2xy(ByVal x1为单个,ByVal y1为单个_
ByVal x2为单体,ByVal y2为单体_
ByVal x_值(单个)
如果x1=x2,则
lin_2xy=[不适用]
其他的
lin_2xy=y1+(y2-y1)/(x2-x1)*(x_值-x1)
如果结束
端函数
函数排序然后插值(ByVal x作为对象,ByVal y作为对象,ByVal x作为单个值)
'插入声明
Dim i作为“整数”计数器。
将当前_x调暗为单个'x值
将下一个x调暗为单个“下一个更高的x值”
将电流_y调暗为单个y值
将下一个y调暗为单个“下一个更高的y值”
Dim LFound为布尔'=如果找到则为true。
Dim matrix()作为变量
矩阵=组织(x个单元格)
LFound=False
对于i=1到UBound(矩阵)
match_value=Application.WorksheetFunction.match(i,矩阵,0)
next\u match=Application.WorksheetFunction.match(i+1,矩阵,0)
当前_x=x.单元格(匹配_值).value
Next_x=x.cells(Next_match).Value
当前单元格(匹配值)。值
Next_y=y.cells(Next_match).Value

如果((当前_x-x_值)*(下一个_x-x_值)如果有帮助,您可以在excel中对一个范围进行排序('Home'选项卡>'sort&Filter>…) 我录制了一个简单的宏(在给定的选定范围内从a到Z排序):

我认为你使用了太多的工作表功能,但实际上我没有完全达到你的目标。。。 在模块开头使用Option explicit

函数返回您可能想要声明的值(至少对我们来说更容易阅读)

在LFound=True之后,也许可以为添加退出

Array_Size = Application.WorksheetFunction.Count(x.cells) + Application.WorksheetFunction.CountBlank(x.cells)
确实是这样写的:

'assuming x is a range or a worksheet, and not an object like you said, its like calling a chicken a bird)

'if x is a worksheet:
with x
    Array_Size = .cells( .rows.count,1).end(xlup).rows
end with

'if x is a range :
Array_Size = x.rows.count 'for counting rows
Array_Size = x.cells.count 'for counting number of cells
也许您可以发布工作表的屏幕截图以提供帮助。
晚上好

根据您的描述,不必过多钻研代码,收藏或词典可能会对您有所帮助。我也很想建议您使用类,但如果您刚刚开始,这些类非常高级。在任何情况下,您是否可以发布一个链接,指向源数据和所需输出的屏幕截图一个,如果不是我,将为你编辑链接中的截图。这样,我们可以了解你正试图做得更好。
Array_Size = Application.WorksheetFunction.Count(x.cells) + Application.WorksheetFunction.CountBlank(x.cells)
'assuming x is a range or a worksheet, and not an object like you said, its like calling a chicken a bird)

'if x is a worksheet:
with x
    Array_Size = .cells( .rows.count,1).end(xlup).rows
end with

'if x is a range :
Array_Size = x.rows.count 'for counting rows
Array_Size = x.cells.count 'for counting number of cells