【问题标题】:VBA not updating Excel rows referring to other sheets in same workbook when sorting rows alphabetically按字母顺序对行进行排序时,VBA 不更新引用同一工作簿中其他工作表的 Excel 行
【发布时间】:2018-03-18 20:49:07
【问题描述】:

我遇到了问题,当按字母顺序排列行时,Excel 没有更新引用同一工作簿中其他工作表的行。

我有一个用户表单,其中有一个按钮 insertCM,代码如下:

Private Sub insertButton_Click()

    ActiveCell.EntireRow.Select
    Selection.Insert Shift:=xltoDown

    Range("A9:AK9").Copy
    Range("A8:AK8").Select
    Selection.PasteSpecial Paste:=xlPasteFormulas
    Selection.PasteSpecial Paste:=xlPasteFormats

    Range("C10").Copy
    Range("C8:C9").Select
    Selection.PasteSpecial Paste:=xlPasteFormulas

    Range("H9:AK9").Copy
    Range("H8:AK8").Select
    Selection.PasteSpecial Paste:=xlPasteAll

    nomCM = Empty
    CXinitial = Empty
    resteCX = Empty
    CCselect = Empty
    C4initial = Empty
    resteC4 = Empty
    compteurCT = Empty

    Range("A8").Activate
    ActiveCell.RowHeight = 18.6

    For i = 2 To ThisWorkbook.Sheets.Count

        With Sheets(i).Select

            emptyRow = Range("A9").End(xlDown).Offset(0, 2).Row
            Range("A9:AL" & emptyRow).Sort _
                Key1:=Range("A9"), Order1:=xlAscending

            Set SearchRange = Range("A8", Range("A200").End(xlUp))
            Set FindRow = SearchRange.Find(nomCM, LookIn:=xlValues, LookAt:=xlWhole)
            Range("A" & FindRow.Row).Select
            ActiveCell.EntireRow.Activate

        End With

    Next i

    Sheet2.Select

    End
End Sub

用户表单用于同时在多个工作表中插入新客户。 Textbox 在空白行中插入名称、成本中心等,insertButton 插入新行,将插入在 row 8 中的数据转到 row 9。之后,代码将所有行按字母顺序排列,因此row 9 中的新客户端会转到新客户端,并且包含公式的单元格会更改行号。

但是,某些工作表的单元格包含对同一行中其他工作表单元格的引用。想象一下:

我插入客户名称"LORUM" "Cost Center 4" 并将他放入row 9 所以公式是:

=$C9-COUNTIF($E9:$P9;"CT")+'Sheet5'!$D9

...但是当它将他的行更改为最后一行时,公式行是:

=$C18-COUNTIF($E18:$P18;"CT")+'Sheet5'!$D9

引用其他工作表时不改变行。

有什么想法吗?

【问题讨论】:

    标签: vba excel


    【解决方案1】:

    看起来您已经付出了很大的努力,但您的代码仍然存在 许多 问题(除了一行之外),我可以保证这些问题的组合会阻止您预期的结果。

    我无法完全修复它,因为有太多错误,我不清楚你要做什么,但希望这能让你走上正确的道路......

    • xlToDown 不是有效的参考。你的意思可能是xlDown

    • 您有许多未声明的变量和对象,例如:i, emptyRow, SearchRange, FindRow, nomCM

    • 你有一些东西(对象?)“设置为空”,没有声明在任何地方使用:CXinitial, resteCX, CCselect, C4initial, resteC4, compteurCT

    • 您的Find 语句正在寻找nomCM,它是(并且从未设置),因此Find 语句将永远找不到任何东西。

      李>
    • 您应该将Option Explicit 放在每个模块的顶部(尤其是在学习或故障排除时)。这将通过“强制”您正确声明和处理所有变量、对象、属性等来防止出现上述问题。

    • 接近尾声时,您引用Sheet2.Select,就好像Sheet2 是一个声明的对象,而不是使用Sheets("Sheet2").Select。我不知道你为什么要在最后选择这张纸。

    • 你有一个 With..End 语句,因为你没有在任何地方用 . 点引用它:With Sheets(i).Select .. End WithSelect 也没有像这样使用。

    • 一个谜End由于某种原因接近尾声。

    此外,您不必要地重复了以下命令:

    ActiveCell.EntireRow.Select
    Selection.Insert Shift:=xlDown
    

    ..而不是:

    ActiveCell.EntireRow.Insert Shift:=xlDown
    

    还有一个例子,all这个:

    Range("A9:AK9").Copy
    Range("A8:AK8").Select
    Selection.PasteSpecial Paste:=xlPasteFormulas
    Selection.PasteSpecial Paste:=xlPasteFormats
    
    Range("C10").Copy
    Range("C8:C9").Select
    Selection.PasteSpecial Paste:=xlPasteFormulas
    
    Range("H9:AK9").Copy
    Range("H8:AK8").Select
    Selection.PasteSpecial Paste:=xlPasteAll
    

    ...而不是:

    Range("A9:AK9").Copy
    Range("A8:AK8").PasteSpecial xlPasteValuesAndNumberFormats
    
    Range("C10").Copy
    Range("C8:C9").PasteSpecial Paste:=xlPasteFormulas
    
    Range("H9:AK9").Copy Range("H8:AK8")
    

    通过谷歌搜索您不熟悉的每个命令的文档,所有这些都会更清楚,例如:

    所有的 ActiveCellThisWorkbook 引用都很麻烦,但同样,我不知道如何处理它们,因为我不知道你的工作簿。

    缩进(和一般组织)也非常重要。它可能不会改变代码的运行方式,但会帮助您(和其他人)更轻松地追踪现有和潜在的问题。


    这是您尽我所能清理的代码:

    Option Explicit 'this line goes at the very top of the module
    
    
    Private Sub insertButton_Click()
    
        Dim i As Long, emptyRow As Long, SearchRange As Range, FindRow As Range, nomCM
    
        nomCM = Empty
    
        ActiveCell.EntireRow.Insert Shift:=xlDown
    
        Range("A9:AK9").Copy
        Range("A8:AK8").PasteSpecial xlPasteValuesAndNumberFormats
    
        Range("C10").Copy
        Range("C8:C9").PasteSpecial Paste:=xlPasteFormulas
    
        Range("H9:AK9").Copy Range("H8:AK8")
        Range("A8").RowHeight = 18.6
    
        For i = 2 To ThisWorkbook.Sheets.Count
    
            With Sheets(i)
                emptyRow = .Range("A9").End(xlDown).Offset(0, 2).Row
                .Range("A9:AL" & emptyRow).Sort Key1:=.Range("A9"), Order1:=xlAscending
    
                Set SearchRange = .Range("A8", .Range("A200").End(xlUp))
                Set FindRow = SearchRange.Find(nomCM, LookIn:=xlValues, LookAt:=xlWhole)
                .Range("A" & FindRow.Row).Select
                ActiveCell.EntireRow.Activate
            End With
    
        Next i
    
        Sheets("Sheet2").Select
    
    End Sub
    

    【讨论】:

    • 感谢您写出这么长的答案。但是: · 声明了对象。
    • · nomCM 存在并且 Find 找到我希望它找到的内容。 · 我选择工作表是因为我希望它在用户窗体关闭和结束时显示。再次感谢您的语法更正。但最重要的是,你的代码不像我的那样工作。您的只是在所选的第一张纸中插入一个新行,而不是在所有表格中。我的问题是在按字母顺序对项目列表进行排序时,公式没有引用其他工作表中的好行。其他方式,谢谢。
    【解决方案2】:

    根据我的测试,排序实际上不会改变其他工作表直接引用

    因此您可能希望使用 OFFSET 来继续引用实际的当前行索引

    代替:

    =$C9-COUNTIF($E9:$P9;"CT")+'Sheet5'!$D9
    

    使用

    =$C9-COUNTIF($E9:$P9;"CT")+ OFFSET('Sheet5'!$D1,ROW()-1,0)
    

    【讨论】:

    • 我尝试了您的解决方案,但它对我不起作用。除了引用其他工作表的单元格引用之外,每个单元格引用都会更改。这是我刚刚做的一个测试的结果公式。 =IF(($C112-$D112)>=10;2;OFFSET('JUIN-18'!$E9;ROW()-1;0))
    【解决方案3】:

    我找到了解决办法:

    =INDIRECT(ADDRESS(ROW();4;3;1;"Sheet5"))
    

    Row() 将始终引用实际单元格的行。

    希望对你有帮助!

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-02-03
      • 2014-09-04
      • 2011-06-04
      • 2015-02-18
      • 2015-01-09
      • 2011-08-29
      • 1970-01-01
      • 2012-02-07
      相关资源
      最近更新 更多