.Text为您提供了一个字符串,表示单元格在屏幕上显示的内容。使用.Text通常不是一个好主意,因为您可能会得到#### .Value2为您提供单元格的底层值(可以是空、字符串、错误、数字(双精度)或布尔值) .Value与.Value2的结果相同,但如果单元格的格式设置为货币或日期,则.Value将为您提供VBA货币(可能会截断小数位)或VBA日期。 使用.Value或.Text通常不是一个好主意,因为您可能无法从像元中获得真实的值,而且它们比.Value2慢 有关更广泛的讨论,请参见我的Text vs Value vs Value2
dynamic x = ws.get_Range("A1").Value2;
object y = ws.get_Range("A1").Value2;
var z = ws.get_Range("A1").Value2;
double d = ws.get_Range("A1").Value2; // Value of a serial is always a double
如果您正在处理单元格的值,则阅读原始.Value2比读取.Value或. Text稍快。如果您正在查找错误,则.Text将返回类似#N/A的文本,并且可以与字符串进行比较,而.Value和. Value 2将无法将其返回值与字符串进行比较。如果您对数据应用了一些自定义单元格格式,则。在构建报表时,文本可能是更好的选择。
Sub Trial_RUN()
For t = 0 To 5
TestValueMethod (True)
TestValueMethod (False)
Next t
End Sub
Sub TestValueMethod(useValue2 As Boolean)
Dim beginTime As Date, aCell As Range, rngAddress As String, ResultsColumn As Long
ResultsColumn = 5
'have some values in your RngAddress. in my case i put =Rand() in the cells, and then set to values
rngAddress = "A2:A399999" 'I changed this around on my sets.
With ThisWorkbook.Sheets(1)
.Range(rngAddress).Offset(0, 1).ClearContents
beginTime = Now
For Each aCell In .Range(rngAddress).Cells
If useValue2 Then
aCell.Offset(0, 1).Value2 = aCell.Value2 + aCell.Offset(-1, 1).Value2
Else
aCell.Offset(0, 1).Value = aCell.Value + aCell.Offset(-1, 1).Value
End If
Next aCell
Dim Answer As String
If useValue2 Then Answer = " using Value2"
.Cells(Rows.Count, ResultsColumn).End(xlUp).Offset(1, 0) = DateDiff("S", beginTime, Now) & _
" seconds. For " & .Range(rngAddress).Cells.Count & " cells, at " & Now & Answer
End With
End Sub
7条答案
按热度按时间ctehm74n1#
.Text
为您提供了一个字符串,表示单元格在屏幕上显示的内容。使用.Text
通常不是一个好主意,因为您可能会得到####
.Value2
为您提供单元格的底层值(可以是空、字符串、错误、数字(双精度)或布尔值).Value
与.Value2
的结果相同,但如果单元格的格式设置为货币或日期,则.Value
将为您提供VBA货币(可能会截断小数位)或VBA日期。使用
.Value
或.Text
通常不是一个好主意,因为您可能无法从像元中获得真实的值,而且它们比.Value2
慢有关更广泛的讨论,请参见我的Text vs Value vs Value2
xu3bshqb2#
除了answer from Bathsheba和MSDN信息外,还提供:
.Value
.Value2
.Text
您可以分析下表以更好地理解这三个属性之间的差异。
k7fdbhmy3#
target.Value
将为您提供Variant
类型target.Value2
也会给予Variant
类型,但Date
会被强制为Double
target.Text
尝试强制为String
,如果基础Variant
不能强制为String
类型,则将失败最安全的做法是
并在尝试显式强制之前使用
VBA.VarType(v)
检查变量的类型。baubqpgj4#
关于C#中的约定,假设你正在阅读一个包含日期的单元格,例如2014-10-22。
使用时:
.Text
,您将获得日期的格式化表示形式,如屏幕上的工作簿所示:2014-10-22.此属性的类型始终为
string
,但可能不总是返回满意的结果。.Value
时,编译器尝试将日期转换为DateTime
对象:**{2014-10-22 00:00:00}**可能仅在阅读日期时有用。.Value2
,给出单元格的真实的基础值。对于日期,它是一个日期序列:41934。根据单元格的内容,此属性可以具有不同的类型。但对于日期序列,类型为double
。所以你可以在
dynamic
,var
,或者object
中检索和存储一个单元格的值,但是要注意,这个值总是有一些固有的类型,你必须对其进行操作。1rhkuytd5#
。Text是格式化单元格的显示值; Value是可能用日期或货币指示符扩充的单元格的值; .Value2是去除了任何无关信息的原始基础值。
如果您正在处理单元格的值,则阅读原始.Value2比读取.Value或. Text稍快。如果您正在查找错误,则.Text将返回类似
#N/A
的文本,并且可以与字符串进行比较,而.Value和. Value 2将无法将其返回值与字符串进行比较。如果您对数据应用了一些自定义单元格格式,则。在构建报表时,文本可能是更好的选择。1sbrub3j6#
出于好奇,我想看看
Value
与Value2
的性能如何。在类似的过程中进行了大约12次试验后,我没有看到任何明显的速度差异,所以我总是建议使用Value
。我使用下面的代码运行了一些不同范围的测试。如果任何人看到任何相反的表现,请张贴。
z2acfund7#
Value2
是 * 几乎总是 * 从VBA读取或写入Excel单元格或范围...的最佳选择。以下每一项都可用于***从范围中读取***:
以下每种方法都可用于将*写入范围:
要从大范围读取多个值,或写入多个值,一次性完成整个操作比逐个单元格执行操作要快几个数量级:
如果
arr
是一个变量类型,那么上面的代码行实际上创建了一个OLE SAFEARRAY structure变量,它包含26列宽、999行高的变量,并将变量arr
指向内存中的SAFEARRAY结构。上面的代码行将整个数组一次性写入工作表,无论数组有多大(只要它适合工作表)。
range对象的默认属性是
Value
属性,因此如果没有为range指定属性,默认情况下会静默引用Value
属性。但是,
Value2
是访问范围值的最快属性,读取该属性时,它将返回真正的基础单元格值。它忽略数字格式、日期、时间和货币,并始终将数字作为VBA Double数据类型返回。由于Value2
尝试执行的工作较少,因此它的执行速度比Value
略快。另一方面,
Value
属性检查单元格值的数字格式是否为日期或时间,并在这些情况下返回VBA日期数据类型的值。如果VBA代码将使用日期数据类型,使用Value
属性检索它们可能是有意义的。将VBA日期数据类型写入单元格将自动使用相应的日期或时间数字格式设置单元格的格式。将VBA货币数据类型写入单元格时,会自动将货币数字格式应用于相应的单元格。同样,
Value
检查单元格货币格式,然后返回VBA货币数据类型的值。这可能会导致精度损失,因为VBA货币数据类型只能识别四个小数位(因为VBA货币数据类型实际上只是一个64位整数,按10000的比例缩放),因此值最多四舍五入到四位。当使用Value
将VBA货币变量写入工作表区域时,该精度将被削减到只有两位小数。只读
Text
属性始终返回VBA字符串数据类型。Range.Text
返回的值是每个单元格中显示内容的文本表示形式,包括数字格式、日期、时间、货币、和错误文本。由于需要隐式或显式强制,因此这不是将数值获取到VBA中的有效方法。Text
将返回#######当列太细时,如果调整某些行高,速度会更慢。与Value
和Value2
相比,Text
总是非常慢。但是,由于Text
保留了单元格值的格式化外观,因此Text
可能很有用,尤其是在使用正确格式化的文本值填充用户窗体控件时。类似地,
Formula
和FormulaR1C1
始终以VBA字符串数据类型返回值。如果单元格包含公式,则Formula
返回其A1样式表示形式,FormulaR1C1
返回其R1C1表示形式。如果单元格具有硬值而不是公式,则Formula
和FormulaR1C1
将忽略所有格式设置,并返回真实的基础单元格值,如下所示Value2
执行...然后进一步将该值转换为字符串。同样,这不是将数值输入VBA的有效方法,因为需要隐式或显式强制。但是,Formula
和FormulaR1C1
* 必须 * 用于读取单元格公式。它们 * 应该 * 用于将公式写入单元格。如果单元格A1包含数值100.25,货币数字格式为$#,##0.00_);($#,##0.00)考虑以下情况: