【问题标题】:Type Mismatch with Sheet Name VBA类型与工作表名称 VBA 不匹配
【发布时间】:2014-05-04 10:48:03
【问题描述】:

我正在尝试编写一个简单的 VBA 代码,该代码在工作簿中运行,删除一些完整的工作表,并清除其他工作表的内容。这是我的代码:

Sub CleanSheets()
Dim x As Integer

x = 1
Do Until x = Sheets.Count
    If Sheets(x).Name = "MIR - Raw" Or "MRR - Raw" Or "MWR - Raw" Or "PL - Raw" Or "SHP - Raw" Then
    'clear them
        Sheets(x).ClearContents
    ElseIf Sheets(x).Name = "Dashboard" Then

    Else
        'delete the sheet
        Application.DisplayAlerts = False
        Sheets(x).Delete
        Application.DisplayAlerts = True
        x = x - 1
    End If
x = x + 1
Loop
End Sub

我在“if sheet(x).name = ...”行中不断收到类型不匹配。我对 Sheets.Names 对象不太熟悉,我怎么把类型搞砸了?

【问题讨论】:

  • 试试 If Sheets(x).Name = "MIR - Raw" Or Sheets(x).Name = "MRR - Raw" Or ... etc.
  • 行得通!不知道为什么...
  • "MIR - Raw" 或 "MRR - Raw" 无法工作,因为 'Or' 需要可以评估为布尔值的表达式,然后执行逻辑析取。 Or 'Or' 运算符还对两个数值表达式中位置相同的位进行按位比较,并在结果中设置相应的位。但是您使用了字符串,因此类型不匹配。
  • 基本上你的代码说:如果 Sheets(x).Name = "MIR - Raw" 或 "MRR - Raw"=true 或 "MWR - Raw"=true 或 "PL - Raw"=true或 "SHP - Raw"=true Then.... ,您无法将字符串与布尔值进行比较

标签: vba excel


【解决方案1】:

您的代码可以正常工作。只需将 If Sheets(x).Name = "MIR - Raw" 或 "MRR - Raw" 或 "MWR - Raw" 或 "PL - Raw" 或 "SHP - Raw" 更改为 If Sheets( x).Name = "MIR - Raw" 或 Sheets(x).Name = "MRR - Raw" 或 Sheets(x).Name = "MWR - Raw" 或 Sheets(x).Name = "PL - Raw" 或Sheets(x).Name = "SHP - Raw"

Sub CleanSheets()
Dim x As Integer

x = 1
Do Until x = Sheets.Count
    If Sheets(x).Name = "MIR - Raw" Or Sheets(x).Name = "MRR - Raw" Or Sheets(x).Name = "MWR - Raw" Or Sheets(x).Name = "PL - Raw" Or Sheets(x).Name = "SHP - Raw" Then
    'clear them
        Sheets(x).ClearContents
    ElseIf Sheets(x).Name = "Dashboard" Then

    Else
        'delete the sheet
        Application.DisplayAlerts = False
        Sheets(x).Delete
        Application.DisplayAlerts = True
        x = x - 1
    End If
x = x + 1
Loop
End Sub

【讨论】:

    【解决方案2】:

    @dee 的回答已解决您的问题,但我看到您检查的名称太多,我想为您的问题提供更优雅的解决方案。

    这个想法很简单:将“If”和“else if”的情况转储到两个单独的数组中,并检查工作表名称是否在每个数组中,并采取相应的动作。由于ElseIf 子句中没有任何动作,我们可以只用If/ElseIf 重写逻辑。我利用this answer中的Jimmy Pena's函数IsInArray进行检查。

    另外,我对代码进行了一些更改,使其更具可读性:

    Sub CleanSheets()
        Dim x As Long   ' Long is safer and faster
        Dim aFirstCategory(4) As String
        Dim aSecondCategory(1) As String
    
        ' Note that checking for the sheet name is usually not very robust.
        ' You might be interested in the Like function to make your checks more flexible
        aFirstCategory(0) = "MIR - Raw"
        aFirstCategory(1) = "MRR - Raw"
        aFirstCategory(2) = "MWR - Raw"
        aFirstCategory(3) = "PL - Raw"
        aFirstCategory(4) = "SHP - Raw"
    
        aSecondCategory(0) = "Dahshboard"
    
        x = 1  ' I would check with ForEach wSheet in Sheets instead
        Do 'Until should go to the end of the loop, else the last sheet will not be checked
            If IsInArray(Sheets(x).Name, aFirstCategory) Then
            'clear them
                Sheets(x).Cells.ClearContents ' Sheets(x).ClearContents gives error I think
            ElseIf not IsInArray(Sheets(x).Name, aSecondCategory) Then
                'delete the sheet
                Application.DisplayAlerts = False
                Sheets(x).Delete
                Application.DisplayAlerts = True
                x = x - 1
            End If
            x = x + 1
        Loop Until x = Sheets.Count
    End Sub
    
    Function IsInArray(stringToBeFound As String, arr As Variant) As Boolean
      IsInArray = (UBound(Filter(arr, stringToBeFound)) > -1)
    End Function
    

    【讨论】:

      猜你喜欢
      • 2020-06-05
      • 1970-01-01
      • 1970-01-01
      • 2013-06-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多