Reputation: 1082
I've reworded my original question.
Sub s()
Dim r As Range
Set r = ActiveSheet.Range("B2:D5")
Debug.Print r.Rows.Count 'returns 4
Debug.Print r.Columns.Count 'returns 3
Debug.Print r.Cells.Count 'returns 12
Debug.Print r.Count 'also returns 12
End Sub
In this particular scenario r.Cells.Count and r.Count are the same. I've come across this in numerous publications, where Cells
is the default item if none is specified.
I'm just wondering if anyone has come across any Microsoft documentation that actually states this - so far I haven't.
Upvotes: 3
Views: 28100
Reputation: 7152
In any situation, you need to ask yourself - what namely do I need? Number of cells? Of rows? Of columns? When you answer, then use appropriate actions:
1) Rows: rng.Rows.Count
2) Columns: rng.Columns.Count
3) Cells: rng.Cells.Count
As a tip, there's caveat with Rows
property. If you want to iterate over rows and process their individual cells, then you must use Cells
property of Range
. Let's say, A1
cell contains value 123
and you want to retrieve it.
Sub G()
Dim rng As Range
Dim firstRow As Range
Dim firstCell As Range
Set rng = [A1:F10]
Set firstRow = rng.Rows(1)
Set firstCell = firstRow(1)
'// DOES NOT WORK: Type mismatch
MsgBox firstCell.Value
Set firstCell = firstRow.Cells(1)
'// WORKS OK! Shows: 123
MsgBox firstCell.Value
End Sub
UPDATE
Also, when dealing with Range (especially in case of autofilter): the Range can contain non-contiguous range. The distinct contiguous ranges are located in Areas
property, thus you will have to first iterate over Areas - and then process your range.
Sub G2
Dim rng As Range, rngArea As Range, cell As Range
For Each rngArea In rng.Areas
For Each cell in rngArea.Cells '//or just "rngArea"
'// Process further
Next
Next
End Sub
Upvotes: 2
Reputation: 34075
You don't actually know what you think you know. :)
Depending on how you assign the range, Range.Count
may return the number of rows or columns, not the number of cells; Cells.Count
will always return the number of cells. To demonstrate, try this:
Sub foo()
Dim rg As Range
Set rg = ActiveSheet.Columns(1)
MsgBox "Cells count is: " & rg.Cells.Count & vbLf & "Count is: " & rg.Count
End Sub
Upvotes: 7
Reputation: 37500
Play with this code to see what they really like:
Option Explicit
Sub s()
Dim rng As Range, rng2 As Range, rng3 As Range
Set rng = Range("B2:D5")
Set rng2 = rng.cells
Set rng3 = rng2.cells 'rng.cells.cells
rng3.cells(1, 1).Select
'rng2.cells(1, 1).Select
'rng.cells(1, 1).Select
End Sub
Bottom line is, that both, rng
and rng.Cells
are Range
objects referring to the same set of cells. Now, since Range
has method Count
, they both have, and obviously they would return exactly the same. The difference is that using Range.Cells.Count
you accessing property of property of Range
object.
Additional resources:
Upvotes: 1