Если массив — ничто, то игнорируйте и переходите к следующему в Excel VBA

#excel #vba

#excel #vba

Вопрос:

Я пытаюсь динамически фильтровать сводную таблицу OLAP. В зависимости от того, устанавливает ли пользователь флажок для определенного месяца или нет, он будет соответствующим образом фильтровать сводку. Можно установить несколько флажков (несколько месяцев). Пример: если они проверят апрель и июнь, сводная таблица OLAP будет отфильтрована по апрелю и июню. Вот мой код:

 Dim Apr18 As String
Dim May18 As String
Dim Jun18 As String

    If Workbooks("A").Sheets("FilePath").CheckApr.Value = True Then
    Apr18 = "[Calendar].[Date Hierarchy].[Year].amp;[2018].amp;[April]"
    End If
    If Workbooks("A").Sheets("FilePath").CheckMay.Value = True Then
    May18 = "[Calendar].[Date Hierarchy].[Year].amp;[2018].amp;[May]"
    End If
    If Workbooks("A").Sheets("FilePath").CheckJun.Value = True Then
    Jun18 = "[Calendar].[Date Hierarchy].[Year].amp;[2018].amp;[June]"
    End If

    Workbooks("B").SlicerCaches("Slicer_Date_Hierarchy") _
    .VisibleSlicerItemsList = Array(Apr18, May18, Jun18)
  

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

 Workbooks("B").SlicerCaches("Slicer_Date_Hierarchy") _ 
.VisibleSlicerItemsList = Array(Apr18, Jun18)
  

Как мне изменить код, чтобы, если флажок снят, игнорировать это поле? Выполнение

  ELse
 Apr18 = ""
  

Не работает.

Примечание: у меня есть 12 месяцев

Ответ №1:

Я думаю, вам нужно будет создавать массив по ходу работы (arr в примере), аналогичный (непроверенный):

 dim arr as variant
Dim Apr18 As String, May18 As String, Jun18 As String
'
redim arr(0)
If Workbooks("A").Sheets("FilePath").CheckApr.Value = True Then
    if not arr(ubound(arr)) = "" then redim preserve arr(ubound(arr) 1) 'redimensions the array to be  1 size larger, preserviing previous data
    arr(ubound(arr)) = "[Calendar].[Date Hierarchy].[Year].amp;[2018].amp;[April]" 'put into array
End If
'add other items
Workbooks("B").SlicerCaches("Slicer_Date_Hierarchy") _
.VisibleSlicerItemsList = arr 'use array you generated
  

Правка1:

Немного измените это, чтобы помочь учесть ваши 12 месяцев:

 dim arr as variant, brr as variant, crr as variant, i as long
brr = array("CheckJan","CheckFeb","CheckMar","CheckApr","CheckMay") 'etc...
crr = array("January","February","March","April","May") 'etc...
redim arr(0)
For i = lbound(brr) to ubound(brr) 'ensure brr and crr are the same length
    If Workbooks("A").Sheets("FilePath").CheckBoxes(brr(i)).Value = True Then
        if not arr(ubound(arr)) = "" then redim preserve arr(ubound(arr) 1) 'redimensions the array to be  1 size larger, preserviing previous data
        arr(ubound(arr)) = "[Calendar].[Date Hierarchy].[Year].amp;[2018].amp;[" amp; crr(i) amp; "]" 'put into array
    End If
next i
Workbooks("B").SlicerCaches("Slicer_Date_Hierarchy").VisibleSlicerItemsList = arr 'use array you generated
  

Комментарии:

1. Это дает мне ошибку, определяемую приложением или объектом, в последней строке

2. @Jade просто об использовании arr для определения срезов? похоже, что у вас была бы аналогичная ошибка в вашем примере кода, если только что-то не было добавлено в массив (возможно, вам потребуется проверить, что имена вошли как ожидалось, используя Debug.Print для каждого элемента массива…

3. Я попробовал код Edit1, и теперь он выдает мне ошибку на . Строка Checkboxes(brr(i)), «Не удается получить свойство Checkboxes класса worksheet»… Как мне использовать Debug. Печатать для каждого элемента?

4. @Jade простое использование кода может быть проблемой, так как может потребоваться внести несколько изменений. В коде Edit1 я предположил, что вы использовали флажки с именами CheckJan и т.д., Что может быть неуместно; это было в первую очередь, как привести пример в виде цикла, чтобы сэкономить на куче дополнительных строк кода. Сосредоточившись на вашем предыдущем комментарии и Debub.Print , в вашем коде вы бы добавили что-то вроде For i = lbound(arr) to ubound(arr) then debug.print arr(i) , и вы должны увидеть значение в Immediate Window . Это позволит вам увидеть, правильный ли формат.

5. @Jade Если возможно, давайте сосредоточимся на первом наборе кода, чтобы мы могли обработать вашу ошибку вокруг ошибки 1004. Была ли ошибка на стороне назначения или проблема заключалась в использовании arr ?

Ответ №2:

Может быть, попробуйте использовать Split для создания массива из строки (которую вы можете создать)? Несколько уродливый пример:

 Dim list As String
list = list amp; "|abc"
list = list amp; "|def"
Dim arr As Variant: arr = Split(Mid(list, 2), "|")  ' assumes list non-empty; ignore first char (delimiter)

Debug.Print arr(0)
Debug.Print arr(1)