使用" TO"了解VBA代码和" STEP"

时间:2014-05-15 21:41:59

标签: excel-vba vba excel

我被赋予此代码以在excel中运行但我试图理解它的含义。我特别想知道变量部分?任何帮助将不胜感激。

sub SortNames

Dim LR As Long

Application.ScreenUpdating = False

Sheets("Stores").Select

LR = Cells(Rows.Count, 1).End(xlUp).Row

For i = LR To 2 Step -1

 'Here is where you can add the names

 If Range("f" & i) <> "Amanda Weaver" And Range("f" & i) <> "Debra Wiesemann" And _
   Range("f" & i) <> "Drew Simpson" And  Range("f" & i) <> "James Howard" And _
   Range("f" & i) <> "Jeff Hruby" And Range("f" & i) <> "Jessica Czupryn" And _
   Range("f" & i) <> "Kevin Janke" And Range("f" & i) <> "Matthew Hudspeath" And _
   Range("f" & i) <> "Maurey Peterson" And Range("f" & i) <> "Noah Hadro" And _
   Range("f" & i) <> "Thomas McHenry" And Range("f" & i) <> "Thomas McHenry" Then

  Range("f" & i).EntireRow.Delete Shift:=xlUp
 End If

Next i

Application.ScreenUpdating = True

End Sub

2 个答案:

答案 0 :(得分:4)

让我们逐行完成代码。如果我太基本,我会提前道歉;但是,其他人可能会发现这些信息很有帮助。

Sub SortNames()

这是程序的名称

Dim LR As Long

创建类型Long的变量以存储行号。

此处使用Long类型的原因(与Integer相对)是因为在较新版本的Excel(2007及更高版本)中,有更多行(1,048,576)可以放入Integer。因此,在Excel中获取行号/计数时应始终使用Long,否则在数字变大时可能会出错。

Application.ScreenUpdating = False

这是一种很好的通用VBA编码技术;它可以防止屏幕在执行过程时闪烁,A提供更愉快的用户体验,而B.使代码运行得更快。请注意,一旦VBA程序完成,ScreenUpdating将自动重新开启(否则您将无法再与Excel交互!)。

Sheets("Stores").Select

显然:选择名为&#34; Stores&#34;的工作表。由于之前的ScreenUpdating行,用户在该过程完成之前不会看到此工作表。我不确定为什么程序的作者选择在这里使用Select;我认为最好使用With... End With块。一般来说,如果可以避免使用Select,那么它应该是。

LR = Cells(Rows.Count, 1).End(xlUp).Row

Cells()函数将返回引用Range的{​​{1}}对象(&#34;商店&#34;)。 ActiveSheet返回第一列中最后一行的Range对象(在Excel 2007或更高版本中为单元格A1048576)。 Cells(Rows.Count, 1)方法从某个起始位置获取行或列中的最后一个使用的单元格。 .End()从下面开始向上获取列中最后一个使用过的单元格。所以整个声明说:

&#34;转到A列的最底部,然后上去,直到找到第一个使用过的单元格,然后告诉我该行号是什么,并将其存储在.End(xlUp)中。&# 34;

顺便说一下:如果我按照上面的建议使用LR块,则该行将是:

With

请注意,此程序的作者似乎知道他们在做什么;发现最后一个使用单元格开头,而不是从整个工作簿中的最后一个单元格开始,是非常好的主意。否则,在其余的过程中,Excel将删除工作簿中的每个空行,无缘无故!除了浪费计算机能力(嗯,谁在乎,对吧?),完成时需要更长时间 。以这种方式从最后一个使用行开始是一种非常好的技术,可以加快程序。

LR = .Cells(Rows.Count, 1).End(xlUp).Row

For i = LR To 2 Step -1 循环从ForLR)开始,执行循环体,然后从For i = LR减去1(i表示< em>&#34;从Step -1中为每一步&#34; 减去1并再次循环。它会在i等于2(i)之前执行此操作。请注意,在上次执行循环时,To 2 = 2(它不跳过 2; i语句包含在内。

To

这只是一个评论。

 'Here is where you can add the names

这是一个相当大的 If Range("f" & i) <> "Amanda Weaver" And Range("f" & i) <> "Debra Wiesemann" And _ Range("f" & i) <> "Drew Simpson" And Range("f" & i) <> "James Howard" And _ Range("f" & i) <> "Jeff Hruby" And Range("f" & i) <> "Jessica Czupryn" And _ Range("f" & i) <> "Kevin Janke" And Range("f" & i) <> "Matthew Hudspeath" And _ Range("f" & i) <> "Maurey Peterson" And Range("f" & i) <> "Noah Hadro" And _ Range("f" & i) <> "Thomas McHenry" And Range("f" & i) <> "Thomas McHenry" Then 语句,用于测试条件或条件,If执行某些代码(如果条件为Then)。您可以猜测True语句在这里做了什么,但无论如何我都会解释。

语句测试以查看If是否评估Range("f & i) <> "*some name*"的值。 True会在Range("f" & i)中返回Range个对象,其中包含列F的单元格地址,行ActiveSheet(请记住ii开始,然后倒数到2)。 LR部分是运算符,这意味着&#34;不等于&#34; <>部分是另一个运营商;它只是同时评估多个条件。因此,如果And运算符两边的两个条件都是AND,则整个语句的计算结果为true。如果其中一个或两个都是True,则会得到错误。将False串在一起时,所有人必须AND才能获得True。所以在第一次通过True循环时,如果行For中的值,列F不等于列表中的任何名称,那么LR语句的正文将执行。

进一步解释这里究竟发生了什么:VBA自动神奇地做了一些事情,以使事情变得更容易。其中之一就是解释你的意图,即使它实际上没有意义。如果您考虑一下,将If对象与&#34; Amanda Weaver&#34; 之类的字符串进行比较并不合理。 Range对象不仅仅是它包含的字符串值;这里有一小部分属于Range而不是其值的东西:公式,名称,背景颜色,文本颜色,文本格式,地址,父级,行和列,还有很多其他的东西。但是,VBA假设当您说Range时,您希望它将单元格F100的与#34; Amanda Weaver&#34;进行比较,而不是任何其他部分

IF Range(F100) <> "Amanda Weaver"

这是 Range("f" & i).EntireRow.Delete Shift:=xlUp 块的正文。如果您的测试条件评估为If,则会出现此处的任何内容。

先前已解释True部分。部分Range("f" & i)意味着删除该EntireRow.Delete对象所属的整个行(请记住:它只删除行,如果,则列F中的值不包含任何列表中的名称)。最后一位Range告诉Excel 如何删除该行。这意味着删除的单元格下方的所有单元格都将向上移动(而不是向左移位的已删除单元格右侧的所有单元格)。

Shift:=xlUp

Duh - 这会结束您的 End If 阻止。

If

请记住,我们整个时间都在Next i 循环中。从For到此点的所有内容都将再次执行,除非For等于比最近值小1的值(直到它等于2,包含)。

i

正如我上面所解释的,这条线可能没有必要。然而,这并不是一件坏事,并且习惯于在代码中明确说出你想要发生的事情,即使它们是自动神奇地发生,这有两个原因:< / p>

  1. 稍后当你回来看看你的代码时,你会忘记你的意思。说真的,你完全是。不要争辩。
  2. 当其他人打算使用您的代码时,您无法假设他们知道您所知道的一切。因此,尽可能明确地表明您打算发生什么。
  3. _

    Application.ScreenUpdating = True
    

    这结束了程序。耶。

    如何学习VBA

    学习VBA可能是令人沮丧的经历(它一直适用于我),找到自己的答案通常会非常令人满意。考虑到这一点,让我提供一些建议。

    我找到了一个获取有关不熟悉的VBA代码含义的信息的好地方是MSDN;然而,实际上在MSDN上找到任何东西都是一个真正的伎俩,所以我改用谷歌。一个好的搜索技术是:&#34; MSDN VBA 这里不熟悉的代码&#34;。

    Here is the MSDN page描述End Sub 循环结构。

    如果您遇到以前未见过的功能或关键字,请花点时间查阅并阅读相关内容。我发现这是最有效的学习技巧之一。

答案 1 :(得分:3)

循环从底部开始(LR是最后一行)并向上行到第2行,每次向行号添加-1。这就是你想要的东西,因为如果你从第2行开始并且每次向下走1行,那么当你删除一行时,所有其余的行都会向上移动,并且在行号上加1会跳过一行。跳过一行不是你想要的,所以你应该从底部开始。

从底部开始向上移动:For i = LR To 2 Step -1

我们说有两行数据(2和3),4是空的。由于LR是3,我们从i = 3开始。如果我们删除第3行,那么第4行将成为第3行,但我们不关心,因为我们将i更改为2并继续。

从顶部开始向下移动:For i = 2 To LR Step 1

我们说有两行数据(2和3),4是空的。因此LR是3.我们从i = 2开始。如果我们删除第2行,那么第3行变为第2行,第4行变为第3行。因此我们将i更改为3,这是一个空行,我们从未有机会检查当前第2行。