简体   繁体   English

Excel VBA - 创建工作表名称数组

[英]Excel VBA - Creating array of worksheet names

I am trying to create an array that contains all of the worksheet names, starting with the 4th worksheet in the active workbook.我正在尝试创建一个包含所有工作表名称的数组,从活动工作簿中的第四个工作表开始。 I'm getting an error on 4th line when I try to redimension the array.当我尝试重新调整数组尺寸时,我在第 4 行遇到错误。 What am I missing?我错过了什么? There are currently 6 worksheets, the 3rd is hidden (in case that changes anything).目前有 6 个工作表,第 3 个是隐藏的(以防发生任何变化)。

Dim i As Integer
Dim sheetsToSkip() As Variant
For i = 4 To Sheets.Count
    ReDim Preserve sheetsToSkip(UBound(sheetsToSkip) + 1)
    sheetsToSkip(UBound(sheetsToSkip)) = Sheets(i).Name
Next i

The problem is that your array sheetsToSkip does not have an upper bound in the first loop cycle yet.问题是您的数组sheetsToSkip在第一个循环周期中还没有上限。 You can check if sheetsToSkip is an array in the first loop and then either dimension it for the first time or resize it.您可以检查sheetsToSkip是否是第一个循环中的数组,然后第一次对其进行标注或调整其大小。

Suggestion for the code:代码建议:

Sub CreateSheetNameArray()
    Dim i As Integer
    'Brakets are removed
    Dim sheetsToSkip As Variant

    For i = 4 To Sheets.Count
        If IsEmpty(sheetsToSkip) Then
            ReDim sheetsToSkip(0 To 0)
        Else
            ReDim Preserve sheetsToSkip(UBound(sheetsToSkip) + 1)
        End If
        sheetsToSkip(UBound(sheetsToSkip)) = Sheets(i).Name
    Next i
End Sub

Be aware that ReDim Preserve is slow.请注意, ReDim Preserve很慢。 If you have a lot of loop cycles, you might consider to just dimension the array before the loop.如果您有很多循环周期,您可能会考虑在循环之前仅对数组进行标注。

Here's a quick couple of examples, if you make a count of the 'valid' sheets first ( if you're avoiding including sheets by name ) - that'll help.这里有几个简单的例子,如果你先计算“有效”的工作表(如果你避免按名称包括工作表) - 这会有所帮助。

-- Version 1 - don't bother checking (just get all sheet names to an array ) -- 版本 1 - 无需检查(只需将所有工作表名称放入数组中)


Sub SheetNamesToArray()

Dim MyWb As Workbook
Dim MySheet As Worksheet
Dim SheetNameArray() As String  ' Array of Sheet Names
Dim LP As Integer ' ( Generic Loop Variable )

Set MyWb = ActiveWorkbook

    ':: Redim to workbook count
    ReDim SheetNameArray(MyWb.Sheets.Count)
    
    ':: Check Array Size
    Debug.Print UBound(SheetNameArray) & " = " & MyWb.Sheets.Count

    ':: Set Array from Sheet Names
    For LP = 1 To MyWb.Sheets.Count
        SheetNameArray(LP) = Sheets(LP).Name
        Debug.Print SheetNameArray(LP) & " :" & Sheets(LP).Name
    Next LP


End Sub

-- Version 2 - Check names, save only valid ( using Inst to test if multiple sheets have a particualar string in name ) -- 版本 2 - 检查名称,仅保存有效(使用 Inst 测试多个工作表是否具有特定的名称字符串)

Sub SheetNamesToArray_And_Ignore_Names()

Dim MyWb As Workbook
Dim MySheet As Worksheet
Dim SheetNameArray() As String  ' Array of Sheet Names
Dim LP, LPx As Integer ' ( Generic Loop Variable(s) )
Dim MyValidSheetsCount As Integer  ' Array Size for only 'valid' sheets


    ':: Apply to active workbook
    Set MyWb = ActiveWorkbook

    For LP = 1 To MyWb.Sheets.Count
        ':: Skip over names to ignore..
        If InStr(1, Sheets(LP).Name, "Four", vbTextCompare) = 0 Then
            '::Iterate count of 'valid' sheets ::
            MyValidSheetsCount = MyValidSheetsCount + 1
        End If
    
    Next LP

    ':: Redim to workbook count
    ReDim SheetNameArray(MyValidSheetsCount)
    
    LPx = 0
    
    ':: Set Array from Sheet Names
    For LP = 1 To MyWb.Sheets.Count

        ':: Same test again, this time add to array, and iterate index variable ( LPX )
        If InStr(1, Sheets(LP).Name, "Four", vbTextCompare) = 0 Then
            SheetNameArray(LPx) = Sheets(LP).Name
            '::Iterate array index ::
            LPx = LPx + 1
        End If

    Next LP

    Debug.Print "Found " & LPx & " valid sheets" & vbNewLine
    
    ':: Check only the 'valid' sheets are recorded
    For LP = 0 To LPx - 1
      Debug.Print "(" & Format(LP, "000#") & ")  : " & SheetNameArray(LP)
    Next LP

End Sub

With VBA there's probably more than a few paths to getting the same result.使用 VBA 可能有不止几条途径可以获得相同的结果。

For the original question, if you're just trying to skip past 4 and aren't concerned they might be out of order, do:对于最初的问题,如果您只是想跳过 4 并且不担心它们可能出现故障,请执行以下操作:


Sub ReallySimpleJustUseNumbers()

':: N.B.  Sheets are indexed starting at 1, arrays begin at 0 ..

Dim MyWb As Workbook
Dim MySheet As Worksheet
Dim SheetNameArray() As String  ' Array of Sheet Names
Dim LP As Integer ' ( Generic Loop Variable )

Set MyWb = ActiveWorkbook

    ':: Are there greater than four sheets in this workbook ?
    If MyWb.Sheets.Count > 4 Then
        ':: Redim to workbook count
        ReDim SheetNameArray(MyWb.Sheets.Count - 4)
    Else
        ':: Polite Exit
        MsgBox "Too Few Sheets buddy"
        Exit Sub
    End If
    
    For LP = 4 To MyWb.Sheets.Count
        SheetNameArray(LP - 4) = MyWb.Sheets(LP).Name
    Next LP
    
    ':: Output array
    For LP = 0 To UBound(SheetNameArray)
        Debug.Print LP & " --- " & SheetNameArray(LP)
    Next LP

End Sub

This'll simply start populating the array as defined as Count of Sheets - Four initial sheets, index starting at 0这将简单地开始填充定义为 Count of Sheets 的数组 - 四个初始工作表,索引从 0 开始

@BigBen is on the right track. @BigBen 走在正确的轨道上。 You only have to ReDim once:您只需 ReDim 一次:

Public Function ListWorkssheets()

    Dim SheetsToSkip()  As String
    Dim Count           As Integer
    Dim Index           As Integer
    
    Count = ThisWorkbook.Worksheets.Count
    ReDim SheetsToSkip(1 To Count)
    
    For Index = 1 To Count
        SheetsToSkip(Index) = ThisWorkbook.Worksheets((Index + 3 - 1) Mod Count + 1).Name
    Next
    
    ' Verify.
    For Index = LBound(SheetsToSkip) To UBound(SheetsToSkip)
        Debug.Print Index, SheetsToSkip(Index)
    Next

End Function

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM