Вопрос по excel, vba – Excel Visual Basic - определить, если диапазон пуст

26

Я не знаю, возможно ли это, но я хочу проверить, является ли диапазон в Excel пустым. Итак, как мне написать, если:

Range("A38":"P38")

Пусто в коде VBA?

Заранее спасибо.

Обратитесь к API (это PIA, но COM, который используется в VBA, должен быть похожим):msdn.microsoft.com/en-us/library/… (свойство Count, возможно) user166390
спасибо я разобрался :) Kano
Я довольно новичок в VBA, так что это не имеет для меня большого смысла :) Kano
Range("A38:P38").Count, увидетьmsdn.microsoft.com/en-us/library/aa139976%28v=office.10%29.aspx user166390

Ваш Ответ

6   ответов
0

ачение из общего числа ячеек.

Sub Emptys()

Dim r As range
Dim totalCells As Integer

'My range To check'
Set r = ActiveSheet.range("A1:B5")

'Check for filled cells'
totalCells = r.Count- WorksheetFunction.CountBlank(r)


If totalCells = 0 Then
    MsgBox "Range is empty"
Else
    MsgBox "Range is not empty"
End If

End Sub
0
Dim cel As Range, hasNoData As Boolean

    hasNoData = True
    For Each cel In Selection
        hasNoData = hasNoData And IsEmpty(cel)
    Next

True если нет клеток вSelection содержит любые данные. Для определенного диапазона просто заменитеRANGE(...) заSelection.

3

если переменная неинициализирована или для нее явно установлено значение Empty; в противном случае возвращается False. False всегда возвращается, если выражение содержит более одной переменной. IsEmpty возвращает значимую информацию только для вариантов. (https://msdn.microsoft.com/en-us/library/office/gg264227.aspx) Таким образом, вы должны проверить каждую ячейку в диапазоне отдельно:

    Dim thisColumn as Byte, thisRow as Byte

    For thisColumn = 1 To 5
        For ThisRow = 1 To 6
             If IsEmpty(Cells(thisRow, thisColumn)) = False Then
                 GoTo RangeIsNotEmpty
             End If
        Next thisRow
    Next thisColumn
    ...........
    RangeIsNotEmpty: 

Конечно, здесь больше кода, чем в решении с функцией CountA, которая считает не пустые ячейки, но GoTo может прерывать циклы, если найдена хотя бы одна непустая ячейка, и выполнять ваш код быстрее, особенно если диапазон большой и вам нужно обнаружить этот случай. Также этот код для меня легче понять, что он делает, чем с функцией Excel CountA, которая не является функцией VBA.

это не всегда работает. Например, если у вас есть диапазон, который не является непрерывным выбором после выбора (скажем, ваш диапазон выбора пропускает 1 ячейку, затем он пропускает 5 ячеек, возвращается к 1 ячейке и т. Д.), То это приведет к ошибке.
Макрос-код Excel (не знаю, возможна ли компиляция) занимает много времени, когда у вас большое количество итераций. Ваше решение необходимо, если вы уже определили, что некоторая ячейка в диапазоне не пуста, и вы хотите обработать ее, но проверка определения, является ли диапазон пустым (т. Е. Если ваш код даже необходим), должна быть быстрее и, возможно, намного быстрее, используя принятый ответ (CountA). Использование одного & quot; родного & quot; функция к циклу VB, который делает то же самое, имеет тенденцию приводить к ускорению времени работы.
47

Sub Empty()
    If WorksheetFunction.CountA(Range("A38:P38")) = 0 Then
        MsgBox "Empty"
    Else
        MsgBox "Not Empty"
    End If
End Sub
Внимание:"Empty()"  не является действительным именем процедуры. @ darren-bartrup-cook, предложенное мной изменение не отклоняется от первоначального замысла поста и не сохраняет его целей.
1

когда абсолютно необходимо, чтобы вы перебирали каждую ячейку в диапазоне вместо использованияCountAзатем гораздо быстрее сначала преобразовать этот диапазон в массив и выполнить цикл по значениям этого массива, чем выполнить цикл во многих диапазонах / ячейках.

Function IsRangeEmpty(ByVal rng As Range) As Boolean

    'Converts a range to an array and returns true if a value is found in said array

    Dim area As Range
    For Each area In rng.areas

        Dim arr As Variant
        arr = area.value

        For i = LBound(arr, 2) To UBound(arr, 2)        'columns
            For j = LBound(arr, 1) To UBound(arr, 1)    'rows

                'if cell is not empty then
                If Len(Trim(arr(j, i))) > 0 Then
                    IsRangeEmpty = False
                    Exit Function
                End If

            Next j
        Next i

    Next area

    IsRangeEmpty = True

En,d Function

Пример того, как его использовать:

Sub Test()
    Debug.Print IsRangeEmpty(Range("A38:P38"))
End Sub

ЕслиRange("A38:P38") пусто, это напечатало быTrue; в противном случае он будет напечатанFalse.

Чтобы справиться со случаем, когда диапазон составляет только одну ячейку, вы можете использовать & quot; If rng.Cells.Count & lt; 2 Тогда ... & quot; и только проверить эту клетку.
3
Dim M As Range

    Set M = Selection

If application.CountIf(M, "<>0") < 2 Then
    MsgBox "Nothing selected, please select first BOM or Next BOM"
Else

'Your code here

End If

If Selection.Rows.Count < 2 
Then End If`

Разъяснение будет предоставлено чуть позже (сейчас я работаю)

@Thor, когда вы ищете решение проблемы в Google, вы получаете эту страницу. Но эта страница не отвечает на эту проблему, поэтому я и ответил на эту проблему. Я считаю, что люди здесь не просто голосуют. Я вижу, что это уже помогло нескольким людям.
Спасибо за ответ, не могли бы вы также немного прояснить, что на самом деле делает сравнение для будущих посетителей? РЕДАКТИРОВАТЬ: Также немного сложно понять, как ваше редактирование вписывается в исходный пример.
Ты все еще работаешь?
@ Jean-Fran & oxCorbett: к сожалению, да, каждый час моей бодрствующей жизни ... Послушай, это помогает тому, кто ищет. Я знаю, что когда я пытался понять это, я снова и снова сталкивался с этой страницей в поиске в Google. Это было именно то решение, которое я искал, поэтому я попытался помочь другим и опубликовать его. Даже если это не 100% прямая помощь, это 1000% косвенная помощь.

Похожие вопросы