excel .text、.value和.value2之间的区别是什么?

sbtkgmzw  于 2023-01-10  发布在  其他
关注(0)|答案(7)|浏览(1044)

.text.value.value2之间的区别是什么?例如何时应该使用target.text、target.value和target.value2?

ctehm74n

ctehm74n1#

.Text为您提供了一个字符串,表示单元格在屏幕上显示的内容。使用.Text通常不是一个好主意,因为您可能会得到####
.Value2为您提供单元格的底层值(可以是空、字符串、错误、数字(双精度)或布尔值)
.Value.Value2的结果相同,但如果单元格的格式设置为货币或日期,则.Value将为您提供VBA货币(可能会截断小数位)或VBA日期。
使用.Value.Text通常不是一个好主意,因为您可能无法从像元中获得真实的值,而且它们比.Value2
有关更广泛的讨论,请参见我的Text vs Value vs Value2

xu3bshqb

xu3bshqb2#

除了answer from Bathsheba和MSDN信息外,还提供:
.Value
.Value2
.Text
您可以分析下表以更好地理解这三个属性之间的差异。

k7fdbhmy

k7fdbhmy3#

target.Value将为您提供Variant类型
target.Value2也会给予Variant类型,但Date会被强制为Double
target.Text尝试强制为String,如果基础Variant不能强制为String类型,则将失败
最安全的做法是

Dim v As Variant
v = target.Value 'but if you don't want to handle date types use Value2

并在尝试显式强制之前使用VBA.VarType(v)检查变量的类型。

baubqpgj

baubqpgj4#

关于C#中的约定,假设你正在阅读一个包含日期的单元格,例如2014-10-22。
使用时:
.Text,您将获得日期的格式化表示形式,如屏幕上的工作簿所示:

2014-10-22.此属性的类型始终为string,但可能不总是返回满意的结果。

.Value时,编译器尝试将日期转换为DateTime对象:**{2014-10-22 00:00:00}**可能仅在阅读日期时有用。
.Value2,给出单元格的真实的基础值。对于日期,它是一个日期序列:41934。根据单元格的内容,此属性可以具有不同的类型。但对于日期序列,类型为double
所以你可以在dynamicvar,或者object中检索和存储一个单元格的值,但是要注意,这个值总是有一些固有的类型,你必须对其进行操作。

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
1rhkuytd

1rhkuytd5#

。Text是格式化单元格的显示值; Value是可能用日期或货币指示符扩充的单元格的值; .Value2是去除了任何无关信息的原始基础值。

range("A1") = Date
range("A1").numberformat = "yyyy-mm-dd"
debug.print range("A1").text
debug.print range("A1").value
debug.print range("A1").value2

'results from Immediate window
2018-06-14
6/14/2018 
43265 

range("A1") = "abc"
range("A1").numberformat = "_(_(_(@"
debug.print range("A1").text
debug.print range("A1").value
debug.print range("A1").value2

'results from Immediate window
   abc
abc
abc

range("A1") = 12
range("A1").numberformat = "0 \m\m"
debug.print range("A1").text
debug.print range("A1").value
debug.print range("A1").value2

'results from Immediate window
12 mm
12
12

如果您正在处理单元格的值,则阅读原始.Value2比读取.Value或. Text稍快。如果您正在查找错误,则.Text将返回类似#N/A的文本,并且可以与字符串进行比较,而.Value和. Value 2将无法将其返回值与字符串进行比较。如果您对数据应用了一些自定义单元格格式,则。在构建报表时,文本可能是更好的选择。

1sbrub3j

1sbrub3j6#

出于好奇,我想看看ValueValue2的性能如何。在类似的过程中进行了大约12次试验后,我没有看到任何明显的速度差异,所以我总是建议使用Value。我使用下面的代码运行了一些不同范围的测试。
如果任何人看到任何相反的表现,请张贴。

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

z2acfund

z2acfund7#

Value2是 * 几乎总是 * 从VBA读取或写入Excel单元格或范围...的最佳选择。

Range.Value2 '<------Best way

以下每一项都可用于***从范围中读取***:

v = [a1]
v = [a1].Value
v = [a1].Value2
v = [a1].Text 
v = [a1].Formula
v = [a1].FormulaR1C1

以下每种方法都可用于将*写入范围:

[a1] = v
[a1].Value = v
[a1].Value2 = v
[a1].Formula = v
[a1].FormulaR1C1 = v

要从大范围读取多个值,或写入多个值,一次性完成整个操作比逐个单元格执行操作要快几个数量级:

arr = [a1:z999].Value2

如果arr是一个变量类型,那么上面的代码行实际上创建了一个OLE SAFEARRAY structure变量,它包含26列宽、999行高的变量,并将变量arr指向内存中的SAFEARRAY结构。

[a1].Resize(UBound(arr), UBound(arr, 2).Value2 = arr

上面的代码行将整个数组一次性写入工作表,无论数组有多大(只要它适合工作表)。
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将返回#######当列太细时,如果调整某些行高,速度会更慢。与ValueValue2相比,Text总是非常慢。但是,由于Text保留了单元格值的格式化外观,因此Text可能很有用,尤其是在使用正确格式化的文本值填充用户窗体控件时。
类似地,FormulaFormulaR1C1始终以VBA字符串数据类型返回值。如果单元格包含公式,则Formula返回其A1样式表示形式,FormulaR1C1返回其R1C1表示形式。如果单元格具有硬值而不是公式,则FormulaFormulaR1C1将忽略所有格式设置,并返回真实的基础单元格值,如下所示Value2执行...然后进一步将该值转换为字符串。同样,这不是将数值输入VBA的有效方法,因为需要隐式或显式强制。但是,FormulaFormulaR1C1 * 必须 * 用于读取单元格公式。它们 * 应该 * 用于将公式写入单元格。
如果单元格A1包含数值100.25,货币数字格式为$#,##0.00_);($#,##0.00)考虑以下情况:

MsgBox [a1].Value                   'Displays:  100.25
MsgBox TypeName([a1].Value)         'Displays: Currency
 
MsgBox [a1].Value2                  'Displays:  100.25
MsgBox TypeName([a1].Value2)        'Displays: Double
 
MsgBox [a1].Text                    'Displays: $ 100.25
MsgBox TypeName([a1].Text)          'Displays: String
 
MsgBox [a1].Formula                 'Displays: 100.25
MsgBox TypeName([a1].Formula)       'Displays: String
 
MsgBox [a1].FormulaR1C1             'Displays: 100.25
MsgBox TypeName([a1].FormulaR1C1)   'Displays: String

相关问题