对于每个循环,不会查看Range.Columns的单个单元格

我有一个函数,通过一系列和两个范围作为参数:

Call settInnISerie(.SeriesCollection("Toppsuging"), r, langsone.Columns(2)) Sub settInnISerie(srs As Series, xverdier As Range, yverdier As Range) Dim c As Range Dim i As Long srs.XValues = xverdier srs.Values = yverdier i = 1 srs.ApplyDataLabels For Each c In yverdier.Offset(0, -1) If Not IsError(c) And i <= srs.Points.Count Then srs.Points(i).DataLabel.Text = "=" & Replace(c.Address(external:=True), "[" & ThisWorkbook.Name & "]", "", 1, -1, vbTextCompare) End If i = i + 1 Next c End Sub 

但是,我在if语句里面的错误,抱怨对象“Point”的方法DataLabel失败。

试图追查错误,我试着打印循环中使用的每个对象的值,并发现,而不是循环在yverdier偏移范围内的每个单元格,如我所料, c引用整个列的第一个直通。

通常当我使用类似的结构时,情况并非如此,为什么在这种情况下foreach -loop行为有所不同? 什么是最简单的方法来解决这个问题?

显然我可以做for i = 1 to c.rows.count...但是我对于什么是VBA的离奇行为感到困惑。

我认为这是预期的行为。

您将yverdier定义为langsone.Columns(2) ,这意味着yverdierRangetypes的集合,集合中有一列(多个单元格)。 我认为你的解释是, yverdier是由yverdier内的单元格组成的单个范围。 langsone.Columns(2)但是两者之间存在细微的差异。

因此,您的For...Each Range For...Each循环将迭代集合中的每个列(单个列)而不是Cells 。 我想你会得到你的愿望行为,如果编码:

 For Each c In yverdier.Offset(0, -1).Cells 

这个示例代码和debugging输出显示了我的意思是在实践中 – 只需创build一个空白的工作簿,并将此代码放在一个Module

 Option Explicit Sub Test() Dim rngSource As Range Dim rng As Range Set rngSource = Sheet1.Range("A1:D3") Debug.Print "Columns:" For Each rng In rngSource.Columns Debug.Print rng.Address Next rng Debug.Print "Rows:" For Each rng In rngSource.Rows Debug.Print rng.Address Next rng Debug.Print "Cells:" For Each rng In rngSource.Cells Debug.Print rng.Address Next rng Debug.Print "No property:" For Each rng In rngSource Debug.Print rng.Address Next rng End Sub 

这将产生以下输出:

 Columns: $A$1:$A$3 $B$1:$B$3 $C$1:$C$3 $D$1:$D$3 Rows: $A$1:$D$1 $A$2:$D$2 $A$3:$D$3 Cells: $A$1 $B$1 $C$1 $D$1 $A$2 $B$2 $C$2 $D$2 $A$3 $B$3 $C$3 $D$3 No property: $A$1 $B$1 $C$1 $D$1 $A$2 $B$2 $C$2 $D$2 $A$3 $B$3 $C$3 $D$3