programing

배열이 비어 있는지 확인(vba excel)

lovejava 2023. 7. 8. 10:25

배열이 비어 있는지 확인(vba excel)

이것들은...그러면 진술들이 제 생각에 잘못된 결과를 얻고 있습니다.첫 번째는 값이 '참'이어야 할 때 '거짓'을 반환하는 것입니다.네 번째 값은 올바른 값을 반환합니다.두 번째와 세 번째는 오류를 반환합니다.

Sub empty_array()
  Dim arr1() As Variant

  If IsEmpty(arr1) Then
    MsgBox "hey"
  End If

  If IsError(UBound(arr1)) Then
    MsgBox "hey"
  End If

  If IsError(Application.match("*", (arr1), 0)) Then
    MsgBox "hey"
  End If

  ReDim arr1(1)
  arr1(1) = "hey"

  If IsEmpty(arr1) Then
    MsgBox "hey"
  End If
End Sub

Arr1은 코드의 첫 번째 문에 의해 'Variant' 배열이 됩니다.

Dim arr1() As Variant

실제 환경에 빈 상자가 존재하는 것처럼 크기가 0인 배열은 비어 있지 않습니다.

변수를 'Variant'로 정의하면 변수가 생성될 때 비어 있습니다.

다음 코드는 "비어 있음"을 표시합니다.

Dim a as Variant

If IsEmpty(a) then
  MsgBox("Empty")
Else
  MsgBox("Not Empty")
End If

여기에 추가하면 어레이가 무엇으로 정의되는지에 따라 달라집니다.고려 사항:

dim a() as integer
dim b() as string
dim c() as variant

'these doesn't work
if isempty(a) then msgbox "integer arrays can be empty"
if isempty(b) then msgbox "string arrays can be empty"

'this is because isempty can only be tested on classes which have an .empty property

'this do work
if isempty(c) then msgbox "variants can be empty"

그래서 우리는 무엇을 할 수 있을까요?예를 들어 VBA에서 오류를 트리거하고 처리할 수 있는지 확인할 수 있습니다.

dim a() as integer
dim bEmpty as boolean

bempty=false

on error resume next
bempty=not isnumeric(ubound(a))
on error goto 0

하지만 이건 정말 서툴러요...더 좋은 해결책은 부울 변수를 선언하는 것입니다(공개 또는 모듈 수준이 가장 좋습니다).배열이 처음 초기화되면 이 변수를 설정합니다.동시에 선언된 변수이기 때문에 값이 손실되면 어레이를 다시 초기화해야 합니다.그러나 초기화된 경우 부울 값만 확인하면 됩니다. 이는 저비용입니다.저렴한 가격이 중요한지, 자주 확인해야 하는지에 따라 다릅니다.

option explicit

'declared at module level
dim a() as integer
dim aInitialised as boolean

sub DoSomethingWithA()
if not aInitialised then InitialiseA
'you can now proceed confident that a() is intialised
end sub

sub InitialiseA()
'insert code to do whatever is required to initialise A
'e.g. 
redim a(10)
a(1)=123
'...
aInitialised=true
end sub

마지막으로 할 수 있는 것은 함수를 만드는 것입니다. 이 경우 함수는 오류 방법에 의존해야 합니다.

function isInitialised(byref a() as variant) as boolean
isInitialised=false
on error resume next
isinitialised=isnumeric(ubound(a))
end function

제가 조금 늦었을 수도 있지만, 다음과 같은 간단한 것들은 문자열 배열에서 작동합니다.

Dim files() As String

files = "..." 'assign array

If Not Not files Then
    For i = LBound(files) To UBound(files)
        'do stuff, array is not empty
    Next
End If

여기까지가 코드입니다.

@jeminar는 위에 가장 좋은 해결책을 가지고 있습니다.

그래도 좀 치웠어요.

FunctionsArray 모듈에 추가하는 것이 좋습니다.

  • isInitialised=false부울은 생성될 때 거짓이므로 필요하지 않습니다.
  • On Error GoTo 0유사한 오류 블록 내부의 코드를 래핑하고 들여씁니다.with가시성을 위한 블록이 방법들은 가능한 한 피해야 하지만... VBA...
Function isInitialised(ByRef a() As Variant) As Boolean
    On Error Resume Next
    isInitialised = IsNumeric(UBound(a))
    On Error GoTo 0
End Function

저는 이렇게 할 것입니다.

if isnumeric(ubound(a)) = False then msgbox "a is empty!"

위의 방법들은 나에게 효과가 없었습니다.이 작업은 다음과 같습니다.

  Dim arrayIsNothing As Boolean

    On Error Resume Next
    arrayIsNothing = IsNumeric(UBound(YOUR_ARRAY)) And False
    If Err.Number <> 0 Then arrayIsNothing = True
    Err.Clear
    On Error GoTo 0

    'Now you can test:
    if arrayIsNothing then ...

VBA의 문제는 동적 어레이와 정적 어레이가 모두 있다는 것입니다.

동적 어레이 예제

Dim myDynamicArray() as Variant

정적 어레이 예제

Dim myStaticArray(10) as Variant
Dim myOtherStaticArray(0 To 10) as Variant

오류 처리를 사용하여 동적 어레이에 대해 어레이가 비어 있는지 확인하지만 정적 어레이는 기본적으로 비어 있지 않습니다. 이러한 모든 항목이 비어 있더라도 어레이에 항목이 있습니다.

그래서 명확성을 위해 함수 이름을 "IsZeroLengthArray"로 지었습니다.

    Public Function IsZeroLengthArray(ByRef subject() As Variant) As Boolean
        'Tell VBA to proceed if there is an error to the next line.
        On Error Resume Next
    
        Dim UpperBound As Integer
        Dim ErrorNumber As Long
        Dim ErrorDescription As String
        Dim ErrorSource As String
    
        'If the array is empty this will throw an error because a zero-length 
          'array has no UpperBound (or LowerBound).
        'This only works for dynamic arrays.  If this was a static array there 
          'would be both an upper and lower bound.
        UpperBound = UBound(subject)


        'Store the Error Number and then clear the Error object 
         'because we want VBA to treat unintended errors normally
        ErrorNumber = Err.Number
        ErrorDescription = Err.Description
        ErrorSource = Err.Source
        Err.Clear
        On Error GoTo 0
    
        'Check the Error Object to see if we have a "subscript out of range" error.  
          'If we do (the number is 9) then we can assume that the array is zero-length.
        If ErrorNumber = 9 Then
            IsZeroLengthArray = True

        'If the Error number is something else then 9 we want to raise 
        'that error again...
        ElseIf ErrorNumber <> 0 Then
            Err.Raise ErrorNumber, ErrorSource, ErrorDescription

        'If the Error number is 0 then we have no error and can assume that the
         'array is not of zero-length
        ElseIf ErrorNumber = 0 Then
            IsZeroLengthArray = False
        End If
    End Function

이것이 나에게 도움이 되었으니 다른 사람들에게도 도움이 되었으면 좋겠습니다.

이거 쓰고 있어요.

If UBound(a) >= 0 Then
    ' not empty
Else 
    ' empty... UBound(a) = -1
End If

IsEmpty(a)내게 도움이 안 됐어요나는 VBA가 싫어요.

Dim arr() As Variant
Debug.Print IsEmpty(arr) ' False
Debug.Print UBound(arr) ' raises error
arr = Array()
Debug.Print IsEmpty(arr) ' False
Debug.Print UBound(arr) ' -1
ReDim Preserve arr(UBound(arr) + 1)
arr(UBound(arr)) = "test"
Debug.Print IsEmpty(arr) ' False
Debug.Print UBound(arr) ' 0

다음 기능은 정적 배열과 동적 배열 모두에서 작동합니다.

     Function array_Empty(testArr As Variant) As Boolean

        Dim i As Long, k As Long, flag As Long

        On Error Resume Next

        i = UBound(testArr)

        If Err.Number = 0 Then

           flag = 0
    
           For k = LBound(testArr) To UBound(testArr)
    
              If IsEmpty(testArr(k)) = False Then
        
                 flag = 1
                 array_Empty = False
                 Exit For
        
              End If
    
            Next k
    
            If flag = 0 Then array_Empty = True

        Else

            array_Empty = True

        End If

     End Function

이것은 나에게 효과가 있었습니다.

Private Function arrIsEmpty(arr as variant)
    On Error Resume Next
    arrIsEmpty = False
    arrIsEmpty = IsNumeric(UBound(arr))
End Function

텐테는 그래서:

Function inic(mtz As Variant) As Boolean
On Error Resume Next
    
    Dim x As Boolean
    x = UBound(mtz):    inic = x
    
End Function
...

if inic(mymtz) then
   debug.print "iniciada"
else
   debug.print "não iniciada"
end if

언급URL : https://stackoverflow.com/questions/26290781/check-if-array-is-empty-vba-excel