5

考虑以下代码段。它将相同的公式写入两个单元格A1,然后A2

Sub Main()
    With Range("A1")
        .Formula = "=1+1"
    End With

    With Range("A2")
        .Formula = "=1+1"
        .Value = .Value
    End With
End Sub

第二个with块使用.Value = .Value计算/执行公式,因此公式从公式栏中消失。请参阅从公式栏中隐藏公式以获得支持性参考。

.Value = .Value 从栏中隐藏公式

现在,添加另一个 with 块

With Range("A3")
     .Formula = "=1+1"
End With
Range("A4") = Evaluate(Range("A3").Formula)

您将公式添加到单元格A3,然后该新单元格的公式将Evaluated()进入另一个单元格A4。结果如图

评估单元格公式

我认为上述类型表明.Value = .ValueEvaluate()做同样的事情。

但是,下面的代码使用上述两种方法从封闭的工作簿中提取值。我book9.xlsm为此示例创建了一个工作簿,其中包含一个hello放入单元格 A1。book9.xlsm是我将从中提取A1' 值的那个。考虑代码

Sub PullValue()
    With Range("A1")
        .Formula = "='C:\Users\admin\Desktop\[book9.xlsm]Sheet1'!A1"
    End With

    With Range("A2")
        .Formula = "='C:\Users\admin\Desktop\[book9.xlsm]Sheet1'!A1"
        .Value = .Value
    End With

    Range("A3").Formula = "='C:\Users\admin\Desktop\[book9.xlsm]Sheet1'!A1"
    Range("A4") = Evaluate(Range("A3").Formula)
End Sub

第一个with块将公式A1从 a 放入单元格的值中book9.xlsm。它被执行,因此拉取的值是hello,但公式栏显示的是实际.FormulaC:\...

第二个with块使用.Value = .Value上面演示的公式评估公式并通过将公式替换为结果来隐藏公式。

Range("A3") 与第一个with块相同。

现在(A4)我遵循与第一个示例(此问题中的第一个片段)相同的原则,Evaluate()但是这次它不起作用。

请查看每个激活的单元格值和公式栏

结果

所以现在,我不能说.Value = .Value等于Evaluate()

Evalutate()的注释说它可以与公式一起使用。但在我展示的示例中它不起作用。

评估() msdn

用作参数的公式是否Evaluate()受到限制?我一直认为 Evaluate 非常强大,但事实证明它.Value = .Value实际上更强大。尽管它们非常相似,但它们在某种程度上有所不同(但我认为这可能是我的错,因为我为此示例选择的公式可能受到限制或限制)。我想我已经展示了是什么让它们同时相似和不同。它仍然像 50%/50%,我无法准确判断它们是否相同。如果有人能够解释这里缺少什么,那就太好了。

4

4 回答 4

8

.value 和 Evaluate 不一样。
Excel 为每个使用的单元格维护一个值和一个公式字符串,您可以使用 Range.Value 和 Range.Formula 独立获取这两者。
当您使用 Application.Evaluate 评估字符串时,该字符串被评估为活动工作表上的公式(因此实际上使用 Worksheet.Evaluate 而不是 Application.Evaluate 更好,而且速度也更快)。
使用 Rng1.Value=Rng2.Value 将值从 Rng2 复制到 Rng1 并覆盖 Rng1 的公式。
使用 Rng1.Value=Evaluate(rng2.Formula) 要求 Excel 从 rng2 检索公式字符串,对其求值并将结果返回给 Rng1。

Evaluate 方法的工作方式与单元格中的公式不完全相同:它有许多您需要注意的“怪癖”(包括它不适用于引用外部封闭工作簿的公式的事实):请参阅我的有关详细信息的博客文章
通常使用 .Value2 而不是 .Value 更好:有关详细信息,请参阅 Value vs Value2

于 2013-07-23T10:25:06.923 回答
1

.Value = .Value(在单元格的With块内)只需将单元格的值设置为其当前值,如果有公式,则覆盖并删除其公式。该.Value属性仅表示单元格的当前值。如果单元格包含尚未计算的公式,例如,如果计算已关闭,则可能不会返回公式结果,而是返回单元格的先前值。

Excel.Application.Evaluate接受一个字符串值,评估字符串的内容,就像它是一个公式或单元格的名称一样,并返回该单元格或公式的值。如果您传递一个无法映射到 Excel 单元格名称或不是有效公式的字符串,您将收到错误消息。的目的Evaluate是允许评估动态创建的公式,而无需将公式写出到单元格中。如果传递一个公式,即使关闭工作簿计算,它也应该返回一个结果,但如果传递一个名称,我希望它返回单元格的当前值,如果工作簿计算关闭,该值可能不会反映引用单元格的期望值。

想必由于.Value一个单元格和Evaluate()可以返回不同的结果,工作表公式评估引擎和Application.Evaluate()引擎是不同的,或者至少有一些不同的元素。

于 2013-07-22T23:32:31.727 回答
1

.Value = .Value并且Evaluate()是不同的。

我认为您对对象及其默认属性有些混淆。

永远记住这两个概念:

  1. VBA 允许您在不指定对象的情况下使用属性和方法。VBA 将使用它们的默认对象。例如,当您使用时,Evaluate()您实际使用Sheet1.Evaluate().

  2. VBA 允许您在不指定属性的情况下使用对象。VBA 将使用它们的默认属性。例如,当您使用时,Range("A1") = 1您实际使用Range("A1").Formula = 1. (你实际上使用Sheet1.Range("A1").Formula = 1!)

回到您的示例,当.Value = .Value您实际执行Range("A2").Value = Range("A2").Value. 单元格的 Value 属性可以是数字、字符串、错误等。当它是数字时,它可能是错误的数字,这不是该单元格中公式的正确结果(例如,因为您已禁用自动计算)。So.Value = .Value等价于.Formula = "<xxx>",其中<xxx>是在单元格上计算的最后一个值。

当您Range("A4") = Evaluate(Range("A3").Formula)要求 Excel 评估公式并将结果分配给Formula范围 A4 的属性时(因为公式属性是范围对象的默认属性。)

于 2013-07-22T19:22:59.787 回答
0

Evaluate 是一个函数,在函数之后使用点 (.) 的东西,称为属性。所以 ".Value",".Formula",".Text" 是您在此处使用的 Range 的属性。

不要把这两件事混为一谈。

函数接受输入,使用其输入变量执行操作并返回结果。它适用于为其配置的数据类型。

.value 是一个不依赖于数据类型的通用属性。它可以是字符串、数字、浮点数或其他。

因此,您可能会从 1 中得到错误,而其他工作绝对没问题。

于 2013-07-22T20:12:21.213 回答