什么时候应该使用Set [例如SpecialCells的返回值]?

时间:2013-07-26 09:19:58

标签: vba excel-vba excel-2010 excel

恐怕我误解了VBA的excel文档,我有这条似乎是错误的一行:

Range a = Selection.SpecialCells(xlCellTypeConstants, 23)

但是这个很好:

Set a = Selection.SpecialCells(xlCellTypeConstants, 23)

文件声明:

  

返回Range 对象,表示与指定类型和值匹配的所有单元格。

但实际上它会返回一个byRef对象,这就是我必须使用Set的原因。

我在这里想念什么?

以下是Excel中的Range.SpecialCells方法帮助:

enter image description here

4 个答案:

答案 0 :(得分:5)

Range a = Selection.SpecialCells(xlCellTypeConstants, 23)

无论数据类型如何,这都不是有效的VBA。你没有像在C#中那样在变量名前面声明变量类型,并且你没有像在VB.NET中那样在声明点初始化变量。

你可以这样做:

Dim a As Range
Set a = Selection.SpecialCells(xlCellTypeConstants, 23)

这会将范围的引用保存到a

你也可以这样做:

Dim a As Variant
a = Selection.SpecialCells(xlCellTypeConstants, 23)

这将在a中保存范围内单元格的2D数组。

  

返回一个Range对象,该对象表示与指定类型和值匹配的所有单元格。

     

但它实际上返回一个byRef对象,这就是我必须使用Set。

的原因

VBA中没有byval对象。所有对象都是byref,当您想要复制对象的引用时,始终使用Set。您需要Set的原因是默认属性。每个对象都可以具有仅在提供对象名称时请求的默认属性。这会产生歧义,因此您需要在需要操作对象引用itselt时说Set,并在需要对象的默认属性时省略SetRange的默认属性为Value

答案 1 :(得分:1)

使用Set关键字分配对象变量。非对象变量(暂时忽略变量)不使用Set关键字

dim a as int
dim b as string
dim c as boolean

a = 1
b = "hello"
c = false

dim a as Range
dim b as Worksheet
dim c as PivotTable

set a = ActiveSheet.Range("a1")
set b = ActiveSheet
set c = ActiveSheet.PivotTables(1)

答案 2 :(得分:1)

enter image description here

Range.SpecialCells Method返回一个Range对象,该对象表示与指定类型和值匹配的所有单元格。 set keyworkd用于指定对象的引用。

VBA中有两种类型的赋值:一种是普通变量,一种是使用Let,另一种是使用Set的对象变量。

普通(字符串,逻辑,数字)变量是指向存储变量的存储器中的位置。

对象变量(在Objects下的语言参考中找到的所有内容)是指向内存中的结构(VTable)的结构,该结构又包含指向对象属性和方法的指针。

参考http://www.excelforum.com/excel-programming-vba-macros/693357-when-to-use-the-keyword-set.html

答案 3 :(得分:0)

不知道这很重要,但Value 不是Range默认属性。 Range的默认属性为_Default

enter image description here

它是这样定义的 _Default([in, optional] VARIANT RowIndex, [in, optional] VARIANT ColumnIndex)它代表特定范围的值数组。

Sub test()

    Dim rng As Range
    Set rng = ActiveSheet.Range("A1:C3")

    ' all cells in range rng become value of 1
    rng.Value = 1

    ' all cells in range rng become now value of 2
    rng.[_Default] = 2

    ' first cell in range rng become value of 3
    rng.[_Default](1, 1) = 3

    ' nothing changes
    rng.Value()(1, 1) = 4

    Dim a1, a2
    ' however both Value and _Default return same array of variants
    a1 = rng.Value
    a2 = rng.[_Default]

End Sub