【问题标题】:How to disable Excel's automatic cell reference change after copy/paste?如何在复制/粘贴后禁用 Excel 自动单元格引用更改?
【发布时间】:2011-10-03 20:19:21
【问题描述】:

我正在处理一个庞大的 Excel 2003 电子表格。有很多非常大的公式,其中包含很多单元格引用。这是一个简单的例子。

='Sheet'!AC69+'Sheet'!AC52+'Sheet'!AC53)*$D$3+'Sheet'!AC49

它们中的大多数都比这更复杂,但这可以很好地了解我正在处理的内容。这些单元格引用很少是绝对的 ($s)。我希望能够在不更改单元格引用的情况下将这些单元格复制到不同的位置。我知道我可以简单地使用 f4 使引用成为绝对引用,但是有很多数据,我以后可能需要使用 Fill。有什么方法可以暂时禁用复制粘贴/填充时更改的单元格引用而不使引用成为绝对引用?

编辑:我刚刚发现您可以通过将单元格内容复制为文本而不是公式来使用 VBA 执行此操作。我不想这样做,因为我想一次复制整个行/列。我缺少一个简单的解决方案吗?

【问题讨论】:

  • 好问题! VBA 中的循环不能解决您剩下的问题吗?

标签: excel excel-formula reference cell copy-paste


【解决方案1】:

我刚才在类似情况下使用的简单解决方法:

  1. 复制工作表。
  2. 将复制工作表(例如Copy of Sheet1)中包含公式的单元格剪切并粘贴到原始工作表中。
  3. 从新粘贴的公式中删除所有出现的重复工作表名称;例如查找并用空字符串(即空白)替换所有出现的搜索词 'Copy of Sheet1'!
  4. 删除重复的工作表进行清理。

注意:如果您的工作表名称缺少空格,则无需使用单引号/撇号 (')。

您的单元格引用现在被复制而不被更改。

【讨论】:

    【解决方案2】:

    我发现这个解决方案可以自动化@Alistair Collins 解决方案。

    基本上你会将任何公式中的 = 更改为 *,然后进行粘贴,然后将其改回

            Dim cell As Range
    
    msgResult = MsgBox("Yes to lock" & vbNewLine & "No unlock ", vbYesNoCancel + vbQuestion, "Forumula locker")
    
    If msgResult = vbNo Then
        For Each cell In Range("A1:i155")
            If InStr(1, cell.Value, "*") > 0 Then
                cell.Formula = Replace(cell.Formula, "*", "=")
            End If
        Next cell
    ElseIf msgResult = vbYes Then
        For Each cell In Range("A1:i155")
            If cell.HasFormula = True Then
                cell.Formula = Replace(cell.Formula, "=", "*")
            End If
        Next cell
    End If
    

    【讨论】:

      【解决方案3】:

      这个宏完成了整个工作。

      Sub Absolute_Reference_Copy_Paste()
      'By changing "=" in formulas to "#" the content is no longer seen as a formula.
      ' C+S+e (my keyboard shortcut)
      
      Dim Dummy As Range
      Dim FirstSelection As Range
      Dim SecondSelection As Range
      Dim SheetFirst As Worksheet
      Dim SheetSecond As Worksheet
      
      On Error GoTo Whoa
      
      Application.EnableEvents = False
      
      ' Set starting selection variable.
      Set FirstSelection = Selection
      Set SheetFirst = FirstSelection.Worksheet
      
      ' Reset the Find function so the scope of the search area is the current worksheet.
      Set Dummy = Worksheets(1).Range("A1:A1").Find("Dummy", LookIn:=xlValues)
      
      ' Change "=" to "#" in selection.
      Selection.Replace What:="=", Replacement:="#", LookAt:=xlPart, _
          SearchOrder:=xlByRows, MatchCase:=False, SearchFormat:=False, ReplaceFormat:=False
      
      ' Select the area you want to paste the formulas; must be same size as original
        selection and outside of the original selection.
      Set SecondSelection = Application.InputBox("Select a range", "Obtain Range Object", Type:=8)
      Set SheetSecond = SecondSelection.Worksheet
      
      ' Copy the original selection and paste it into the newly selected area. The active
        selection remains FirstSelection.
      FirstSelection.Copy SecondSelection
      
      ' Restore "=" in FirstSelection.
      Selection.Replace What:="#", Replacement:="=", LookAt:=xlPart, _
      SearchOrder:=xlByRows, MatchCase:=False, SearchFormat:=False, ReplaceFormat:=False
      
      ' Select SecondSelection.
      SheetSecond.Activate
      SecondSelection.Select
      
      ' Restore "=" in SecondSelection.
      Selection.Replace What:="#", Replacement:="=", LookAt:=xlPart, _
      SearchOrder:=xlByRows, MatchCase:=False, SearchFormat:=False, ReplaceFormat:=False
      
      ' Return active selection to the original area: FirstSelection.
      SheetFirst.Activate
      FirstSelection.Select
      
      Application.EnableEvents = True
      
      Exit Sub
      
      Whoa:
      ' If something goes wrong after "=" has been changed in FirstSelection, restore "=".
      FirstSelection.Select
      Selection.Replace What:="#", Replacement:="=", LookAt:=xlPart, _
          SearchOrder:=xlByRows, MatchCase:=False, SearchFormat:=False, ReplaceFormat:=False
      
      End Sub
      

      请注意,当您进行新选择时,您必须与原始选择的大小和形状相匹配。

      【讨论】:

        【解决方案4】:

        来自http://spreadsheetpage.com/index.php/tip/making_an_exact_copy_of_a_range_of_formulas_take_2

        1. 将 Excel 置于公式视图模式。执行此操作的最简单方法是按 Ctrl+` (该字符是“向后撇号”,通常位于带有 ~(波浪号)的同一个键上.
        2. 选择要复制的范围。
        3. Ctrl+C
        4. 启动 Windows 记事本
        5. Ctrl+V 将复制的数据粘贴到记事本中
        6. 在记事本中,按 Ctrl+A 然后按 Ctrl+C 复制文本
        7. 激活 Excel 并激活要粘贴公式的左上角单元格。并且,确保您要复制到的工作表处于公式视图模式。
        8. Ctrl+V粘贴。
        9. Ctrl+` 可退出公式视图模式。

        注意:如果粘贴回 Excel 的操作无法正常工作,可能是因为您最近使用了 Excel 的文本到列功能,并且 Excel 试图通过记住您上次分析数据的方式来提供帮助。您需要启动“将文本转换为列向导”。选择分隔选项,然后单击下一步。清除除 Tab 之外的所有 Delimiter 选项复选标记。

        或者,来自http://spreadsheetpage.com/index.php/tip/making_an_exact_copy_of_a_range_of_formulas/

        If you're a VBA programmer, you can simply execute the following code: 
        With Sheets("Sheet1")
         .Range("A11:D20").Formula = .Range("A1:D10").Formula
        End With
        

        【讨论】:

        • 看起来您可以粘贴到不在公式视图模式下的工作表中;尽管其他一切都是绝对必要的,但严格遵守这一点并没有什么坏处。 +1,因为这非常有帮助且易于理解。我不明白为什么 Excel 假定我们要引用另一个文件中的单元格,但至少有一个很好的解决方法。
        • 这个答案很棒 - 我希望我能接受它作为原始海报。我是一名程序员,所以 VBA 不会吓到我,但如果可以避免的话,我不会只使用它来复制和粘贴一些单元格......确实应该有一个“粘贴而不更新公式”选项构建在 Excel 中。
        • @JPhi1618 是的。我不知道为什么他们不会在不更新公式的情况下粘贴粘贴。最让我困扰的是,除了电子表格提供商、MS Office、Google Sheet 或 WPS Office 之外,它们只是相互重复。我怀念他们用技术和功能进行创新的时候。他们在每个版本中都进行了巨大的改进。但是缺少一些基本的东西。
        【解决方案5】:

        单击要复制的单元格。在公式栏中,突出显示公式。

        Ctrl C

        按退出键(让您不再主动编辑该公式)。

        选择新单元格。 Ctrl V。

        【讨论】:

          【解决方案6】:

          尚未签入 Excel,但这在 Libreoffice4 中有效:

          地址重写的整个过程都发生在连续
          (a1) 切
          (a2) 粘贴

          你需要在中间插入一些东西来打断连续性:
          (b1) 切
          (b2) 选择一些空单元格(超过 1 个)并拖动(移动)它们
          (b3) 粘贴

          步骤 (b2) 是即将自我更新的单元格停止跟踪的地方。快速简单。

          【讨论】:

          • 我认为这个答案是不合适的,因为它甚至没有经过测试。
          • Fjodr,我没有 excel。你能测试一下吗?我希望它能够工作,这听起来像是所有提议的解决方案中最简单的。投票最多的答案包括 9 个步骤!我的要容易得多。请试一试!
          【解决方案7】:

          在执行操作时使用查找/替换来禁用公式是很常见的。例如,使用转置进行复制。通过在其前面放置一些占位符(例如“$ =”)来禁用该公式。一旦操作完成,查找替换可以摆脱这些。

          这个 vba 只是自动查找/替换活动工作表。

          ' toggle forumlas on active sheet as active/ inactive
          ' by use of "$=" prefix
          
          Sub toggle_active_formulas()
              Dim current_calc_method As String
              initial_calc_method = Application.Calculation
              Application.Calculation = xlCalculationManual
              Dim predominant As Integer
              Dim c As Range
              For Each c In ActiveSheet.UsedRange.Cells
                  If c.HasFormula Then
                      predominant = predominant + 1
                  ElseIf "$=" = Left(c.Value, 2) Then
                      predominant = predominant - 1
                  End If
              Next c
              If predominant > 0 Then
                  For Each c In ActiveSheet.UsedRange.Cells
                      On Error Resume Next
                      If c.HasFormula Then
                          c.Value = "$" & c.Formula
                      End If
                  Next c
              Else
                  For Each c In ActiveSheet.UsedRange.Cells
                      On Error Resume Next
                      If "$=" = Left(c.Value, 2) Then
                          c.Formula = Right(c.Value, Len(c.Value) - 1)
                      End If
                  Next c
              End If
              Application.Calculation = initial_calc_method
          End Sub
          

          【讨论】:

          • 你能在这篇文章中添加更多细节吗?
          【解决方案8】:

          我发现了另一种非常简单的解决方法: 1.剪切内容 2.将它们粘贴到新位置 3. 将您刚刚粘贴的内容复制到您想要的新位置。 4.撤消剪切粘贴操作,将原始内容放回您获得它们的位置。 5. 将剪贴板中的内容粘贴到同一位置。这些内容将有原始引用。

          看起来很多,但使用键盘快捷键超级快: 1. Ctrl-x, 2. Ctrl-v, 3. Ctrl-c, 4. Ctrl-z, 5. Ctrl-v

          【讨论】:

            【解决方案9】:

            这个简单的技巧很有效:复制和粘贴。不要剪切和粘贴。粘贴后,重新选择您复制的部分并转到 EDIT,向下滑动到 CLEAR,然后 CLEAR CONTENTS。

            【讨论】:

              【解决方案10】:

              试试这个: 左键单击选项卡,复制整个工作表,然后剪切要保持不变的单元格并将它们粘贴到原始工作表中。

              【讨论】:

                【解决方案11】:

                我来到这个网站是为了寻找一种无需更改单元格引用即可轻松复制的方法。但现在我认为我自己的解决方法比大多数这些方法更简单。我的方法依赖于 Copy 更改引用但 Move 没有更改的事实。这是一个简单的例子。

                假设您在 A 列和 B 列中有原始数据,在 C 列中有一个公式(例如 C=A+B),并且您希望在 F 列中有相同的公式,但是从 C 复制到 F 会导致 F=D+E。

                1. 将 C 的内容复制到任何空的临时列,例如 R。相对引用将更改为 R=P+Q,但即使它被标记为错误也会忽略这一点。
                2. 返回到 C 并将其移动(而不是复制)到 F。公式应保持不变,因此 F=A+B。
                3. 现在转到 R 并将其复制回 C。相对引用将恢复为 C=A+B
                4. 删除 R 中的临时公式。
                5. Bob 是你的叔叔。

                我已经对一系列单元格进行了此操作,因此我想它几乎可以在任何复杂程度下工作。您只需要一个空白区域来停放复制的牢房。当然,你必须记住你把它们放在哪里。

                【讨论】:

                • 描述不简单 :) 如果要将第 1 行(引用第 2 行)复制到第 11 行,则: 1. 将其复制到第 11 行,然后它将引用第 12 行。 2 . 剪切并粘贴到第21行,那么它仍然会引用第12行。 3. 将它从21复制到第11行,然后它会根据需要引用第2行。
                • 对我来说似乎很简单,复制到偏移量,移动原始,复制偏移量,删除偏移量。
                • 对我来说这是最简单的,因为我几乎可以闭着眼睛双手放在键盘上。另外,您可以一次完成整个区域或行:Ctrl+C -> Ctrl+V 然后 Ctrl+X -> Ctrl+V,根据需要重复。例如。要复制表中的某些行并引用表外,这是最好的:它更新选择内的引用,同时保留选择外的引用。
                【解决方案12】:

                一个非常简单的解决方案是选择您要复制的范围,然后查找并替换 (Ctrl + h),将 = 更改为公式中未使用的另一个符号(例如 #) - 从而停止它是一个活跃的公式。

                然后,将所选范围复制并粘贴到新位置。

                最后,Find and Replace 将 # 在原始范围和新范围中更改回 =,从而将两个范围再次恢复为公式。

                【讨论】:

                • 到目前为止,很遗憾,这是我最满意的解决方案。使用简单的替代快捷方式会很方便。
                【解决方案13】:

                我认为您对您在编辑中提到的解决方法感到困惑。

                我会首先将工作表上的每个公式转换为大致如下所示的文本:

                Dim r As Range
                
                For Each r In Worksheets("Sheet1").UsedRange
                    If (Left$(r.Formula, 1) = "=") Then
                        r.Formula = "'ZZZ" & r.Formula
                    End If
                Next r
                

                'ZZZ 使用' 表示文本值,ZZZ 作为我们想要将文本转换回公式时可以查找的值。显然,如果您的任何单元格实际上以文本 ZZZ 开头,则将 VBA 宏中的 ZZZ 值更改为其他值

                重新排列完成后,我会将文本转换回如下公式:

                For Each r In Worksheets("Sheet1").UsedRange
                    If (Left$(r.Formula, 3) = "ZZZ") Then
                        r.Formula = Mid$(r.Formula, 4)
                    End If
                Next r
                

                此方法的一个真正缺点是在重新排列时您无法看到任何公式的结果。例如,当您从文本转换回公式时,您可能会发现有大量 #REF 错误。

                分阶段处理此问题并经常转换回公式以检查是否没有发生灾难可能会有所帮助

                【讨论】:

                  猜你喜欢
                  • 2021-03-16
                  • 2017-12-30
                  • 1970-01-01
                  • 2012-08-21
                  • 1970-01-01
                  • 1970-01-01
                  • 1970-01-01
                  • 2016-12-25
                  • 2017-09-15
                  相关资源
                  最近更新 更多