在Excel中,使用“Range.Replace”方法替换字符,但不影响公式

时间:2016-01-06 06:15:05

标签: excel vba excel-vba

我想为Excel(2010)创建一个宏,用拉丁字母的字符替换西里尔字母的等价物。

乍一看,这似乎很容易,例如像这样:

ActiveSheet.Range("A1:Z500").Replace "sht", ChrW(1097) '--> щ
ActiveSheet.Range("A1:Z500").Replace "Sht", ChrW(1095) '--> Щ
'And so on for all relevant characters and character combinations

但是,当我在活动工作表上运行它时,不仅会影响单元格值,还会影响公式。这使他们毫无价值,因为例如总和(B1:B3)将变为Сум(Б1:Б3)[即使用西里尔字母],对于Excel来说,这是胡言乱语。

因此问题:有没有办法告诉Excel只对单元格值使用Replace方法,而不是公式?

注意:一个脏的解决方法可能是包括一个过程,该过程首先检查范围中的每个单元格是否以“=”开头,如果是,则保持单元格内容不变。但也许有一种更好的,更少的自酿方式?

2 个答案:

答案 0 :(得分:5)

Range.Replace将始终搜索公式。

HasFormula对象中有Range个属性。但是为了使用它,你必须迭代给定Range中的所有单元格。如果此Range非常大,那么如果您在每个单元格中尝试Replace,则需要很长时间。所以我只会尝试Replace如果单元格不为空,不是数字而且没有公式。

Sub test()

 Dim oRange As Range

 For Each oRange In ActiveSheet.Range("A1:Z500")
  If Not IsEmpty(oRange) And Not IsNumeric(oRange.Value) And Not oRange.HasFormula Then
    oRange.Replace What:="sht", Replacement:=ChrW(1097), MatchCase:=True
    oRange.Replace What:="Sht", Replacement:=ChrW(1065), MatchCase:=True
  End If
 Next

End Sub

哦,如果替换应区分大小写,则必须设置MatchCase

第二种方法:

您也可以使用VBA Replace代替Range.Replace,如另一个答案中所示。但不是Range.Formula而是Range.Value

这可能会更快。

Sub test2()

 Dim oRange As Range

 For Each oRange In ActiveSheet.Range("A1:Z500")
  If Not IsEmpty(oRange) And Not IsNumeric(oRange.Value) And Not oRange.HasFormula Then
    oRange.Value = Replace(oRange.Value, "sht", ChrW(1097), , , vbBinaryCompare)
    oRange.Value = Replace(oRange.Value, "Sht", ChrW(1065), , , vbBinaryCompare)
  End If
 Next

End Sub

答案 1 :(得分:0)

你必须查看.Formula属性,默认的Range结果给出.Value(即结果),而不是值。

我建议使用如下的循环:

For Each cell In ActiveSheet.Range("A1:Z500")
    cell.Formula = Replace(cell.Formula, "sht", ChrW(1097))
    cell.Formula = Replace(cell.Formula, "Sht", ChrW(1095))
Next