我正在使用VBA在Excel中处理宏。我有一系列数字,如:
180, 190, 300, 390, 400, 430, ...
然后我有一个变量,其值为307
或389
或425
。如何在不使用一堆If
语句的情况下将此数字向下舍入到数组中包含的下一个最小数字?
例如,我需要更改:
307 -> 300
389 -> 300
425 -> 400
与使用一长串逻辑语句相比,更快的方法是什么?
答案 0 :(得分:2)
如果您的数组已排序,则可以使用HLOOKUP()
。如果为最后一个参数指定True
,则它将匹配最接近的上一个值。例如:
Debug.Print WorksheetFunction.HLookup(307, Array(180, 190, 300, 390, 400, 430), 1, True)
输出:
300
您只需要防范低于最低数字的数字(在本例中为180)。因此,您可能希望使用值0
启动数组。
答案 1 :(得分:0)
你可以这样做。
Private Sub CommandButton20_Click()
Dim aValues(1 To 5) As Integer
Dim i As Integer
aValues(1) = 180
aValues(2) = 190
aValues(3) = 300
aValues(4) = 390
aValues(5) = 400
Dim iFindValue As Integer
iFindValue = 310
'First make sure we have a valid value to check for.
If aValues(1) > iFindValue Then
MsgBox ("Lowest value in the array is greater than variable.")
Exit Sub
End If
'Loop through the array
For i = 1 To UBound(aValues)
'If we are at the end of the array, we haven't found it so set the value to the highest slot in the array.
If i = UBound(aValues) Then
iFindValue = aValues(i)
Exit Sub
End If
'If it is in between the current slot value and the next one, set it to the current. Effectively rounding it down.
If aValues(i) < iFindValue And aValues(i + 1) > iFindValue Then
iFindValue = aValues(i)
Exit Sub
End If
Next i
End Sub
你说过你的阵列可以排序,但如果由于某些原因它不是,你可以这样做。
Private Sub CommandButton20_Click()
Dim aValues(1 To 5) As Integer
Dim i As Integer
aValues(1) = 180
aValues(2) = 190
aValues(3) = 300
aValues(4) = 390
aValues(5) = 400
Dim iFindValue As Integer
iFindValue = 310
Dim iTemp As Integer
Dim iDifference As Integer
iDifference = 32000
For i = 1 To UBound(aValues)
'Find the difference
iTemp = iFindValue - aValues(i)
'If it is the smallest difference found so far, record it
If iTemp > 0 And iTemp < iDifference Then
iDifference = iTemp
End If
Next i
'Make the adjustment
iFindValue = iFindValue - iDifference
End Sub
答案 2 :(得分:0)
假设数组已排序,您可以使用:
Function RoundTo(A As Variant, num As Long) As Variant
'returns greatest number in A which is <= num
'returns False if no such number exists
'assumes A is a sorted array of numbers
Dim i As Long
On Error Resume Next
i = Application.WorksheetFunction.Match(num, A, 1)
If Err.Number > 0 Then
RoundTo = False
Exit Function
End If
On Error GoTo 0
RoundTo = A(LBound(A) + i - 1)
End Function
用过:
Sub test()
Dim A As Variant, i As Long
A = Array(12, 15, 19, 25, 39)
Debug.Print RoundTo(A, 45)
Debug.Print RoundTo(A, 18)
Debug.Print RoundTo(A, 12)
Debug.Print RoundTo(A, 11)
End Sub
输出:
39
15
12
False
当数字太小而无法舍入到数字列表中的任何数字时,您当然可以调整它以返回False
以外的内容