Excel VBA范例大全
上QQ阅读APP看本书,新人免费读10天
设备和账号都新为新人

第1部分 单元格选择技巧与选区统计

单元格是Excel 2007储存数据的最小单位,也是电子表格的储存和运算基础。灵活而快速地掌握单元格选择技巧有助于制表效率的提升,以及数据运算的准确性。本部分通过27个实例向读者展示单元格与区域选择及其基本统计方面的运用,让读者迅速掌握并发挥VBA在制表中的优势。

本部分主要知识点:

● 单元格与区域选择技巧

● 多表单元格选择

● 对选区进行基本统计

第1章 单元格与区域选择技巧

对于固定地址的单元格选择,手工操作就能轻易完成。但基于指定条件选择单元格,且条件可能因单元格数据变化而相应变化时,手工操作则会捉襟见肘了。对此,可以利用VBA(Visual Basic for Application)对单元的属性识别来精确且快速地定位。

● 实例1选择A列最后一个非空单元格

● 实例2基于指定位置的偏移量的选取

● 实例3选择当前列最大值

● 实例4选择负数单元格

● 实例5选择单元格所在区域及工作表已用区域

● 实例6选择数组公式区域

● 实例7返回单元格合集与交集

● 实例8选择背景色为黄色的单元格

● 实例9选择字体为蓝色之单元格

● 实例10选择粗线边框之单元格

● 实例11反向选择工作表

● 实例12选择单元格区域但排除首行标题

● 实例13每隔三行选一行

● 实例14选择奇数列

实例1 选择A列最后一个非空单元格

【技巧说明】 定位至第一行的最后一个有数据的单元格。

【案例介绍】 工厂的产量表数据行一般较多,本例中有350行。当要查看合计项时则需要将光标定位于最后一个非空行,数据如图1.1所示。

图1.1 产量表

【案例实现】 假设当前光标在单元格A350以外的任何区域,实现定位步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码,如图1.2所示。

Sub选择A列最后一个非空单元格()
Range("a1048576").End(xlUp).Select
End Sub

图1.2 VBE环境

[4] 关闭VBE窗口返回到工作表。

[5] 使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,如图1.3所示。

[6] 运行程序后光标将自动跳转至A列最后一个有数据的单元格,即“合计”所在行。

图1.3 运行宏窗口

提示

本实例参见光盘样本:..\第1部分\实例1.xlsm

【相关知识说明】

(1)Range():返回一个Range对象,它代表一个单元格或单元格区域。区域的大小由其参数决定。格式为双引号之中写入单元格地址,如Range("A10");也可以用逗号分隔写入多个单元格地址,如Range("a1,a10,a20") 表示三个单元格。Range()还可以有多个参数,即Range()的嵌套使用,如Range(Range("a1"), Range("a10"))表示单元格区域A1∶A10,共10个单元格,而不是A1和A10两个单元格。

(2)Range("a1048576"):Excel 2003升级至2007后,可用行数从65536行提升至1048576行,所以表示A列最大行数时使用Range("a1048576").Row。

(3)End(xlUp):Range.End属性返回一个Range对象,代表包含源区域的区域尾端的单元格。End有一个参数,代表移动方向,本例中xlUp表示向上,也可以将xlUp改为-4162,功能相同。Range("a1048576").End(xlUp)整句含义则是A列最后一个单元格向上第一个非空单元格。End属性参数列表如下(见表1.1),可以根据不同需求选择相应的参数。

(4)Range.Select:选择单元格。要选择单元格或单元格区域,使用Select方法。要使单个单元格成为活动单元格,请使用Activate方法。它们两者的区别是Select方法可选择多单元格,而Activate方法只能选择单个单元格。

表1.1 End属性参数

实例2 基于指定位置的偏移量的选取

【技巧说明】 选择当前单元格下一行已用区域外第一个空白单元格。

【案例介绍】 常规报表一般是整行或者整列之数据对齐,输入数据时直接按回车键即可跳到下一个输入单元格。但针对特殊状况,如图1.4所示,各行已用单元格数量不同,按回车键时无法每次都进入下一个待输入单元格,从而造成输入效率降低。本案例代码则用来解决此问题。

图1.4 罚金表

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 使用快捷键Ctrl+R,显示工程资源管理器。

[3] 双击左边列表中的“产量表”,打开工作表代码窗口。

[4] 在右边代码窗口输入以下代码,如图1.5所示。

Private Sub Worksheet_Change(ByVal Target As Range)
Cells(Target.Row+1, 16384).End(xlToLeft).Offset(0, 1).Select
End Sub

图1.5 工作表代码窗口

[5] 关闭VBE窗口返回到工作表。

[6] 光标定位至单元格C3,输入任意字符并回车,可以发现程序已激活下一行空白单元格D4;D4中输入数据后光标将定位至单元格C3,完全符合需求。

提示

1.本实例参见光盘样本:..\第1部分\实例2.xlsm。

2.本实例中,在任意单元格输入数据并回车,光标都跳转至下一行已用区域外第一个空白单元格,但某行未输入数据时,按回车键或者键盘上向下箭头键,光标将按常规方式跳转。如果需要光标仍然跳转至下一行已用区域外第一个空白单元格,则必须在当前的空白单元格中以键盘上的Delete键替代回车键或者向下箭头键。

【相关知识说明】

(1)Sub Worksheet_Change(ByVal Target As Range):工作表事件,在工作表中数据被修改时发生。代码加入到Sub Worksheet_Change(ByVal Target As Range)事件中将在工作表中任意单元格数据被修改时就执行代码,而不需要手动运行(见实例1)。需要特别指出的是,单元格中函数与公式结果改变时将不引发此事件。

(2)Cells():单元格对象,等同于Range。如Range("A10")表示单元格A10,Cells(10,1)也表示单元格A10。但它们在使用上有一些区别:Range()代表某一单元格、某一行、某一列、某一选定区域或者某一三维区域。而Cells()带参数时只能表示单个单元格,不带参数时表示工作表中所有单元格,不及range()表示单元格那么灵活。但Cells()的行和列两个参数都是数字变量,较之Range()的一个数字变量和一个字母变量在使用上方便许多,特别是需要单元格循环引用时。

(3)Cells(Target.Row+1, 16384):Target是一个单元格对象,表示当前选中单元格区域;16384表示Excel 2007的最大列数;Cells(Target.Row+1, 16384)则表示相对于当前行的下一行最后一个单元格。

(4)Offset:表示指定单元格区域一定的偏移量位置上的区域,它有两个参数,一个为偏移行数,一个为偏移列数,可以是负数。本例中为偏移1列,从最后一个非空单元格偏移至第一个空白单元格。故使用参数0和1表示行不变,偏移一列。

实例3 选择当前列最大值

【技巧说明】 选择光标所在列的最大值所在的单元格,如果存在多个单元格等于最大值,仅选择第一个。

【案例介绍】 在大容量报表中查找最大值,当数据少时可用目视比较;数据多时,常规办法是先升序排序再找其首行值。但此方法会破坏原工作表数据分布方式。使用VBA处理此类事件则可以得心应手。本例采用实例1之数据,工作表有350行,利用代码循环检测单元格的数据是否等于该列最大值。

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码。

Sub选择当前列最大值()
    Dim rng As Range, rng2 As Range              '声明变量
    Set rng2=Application.Intersect(ActiveCell.EntireColumn,
        ActiveCell.CurrentRegion) '将本列已用区域赋值给rng2
    For Each rng In rng2                          '开始循环检测单元格值
        If rng.Value=WorksheetFunction.Max(rng2) Then  '如果等于最大值
        rng.Select                                 '选择该单元格
        Exit For                                   '退出循环
    End If
    Next
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 光标定位于C列有数据的任意单元格,使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,光标已定位于单元格C310,可以在G1输入公式“=MAX(C:C)”来验证值是否正确,结果如图1.6所示。

图1.6 选择并验算C列最大值

提示

1.本实例参见光盘样本:..\第1部分\实例3.xlsm。

2.代码中单引号后面的文字是当前行代码的含义解释,使用户可以快速了解代码编写者的思路和代码用意。在执行程序时会跳过该文字。

3.本程序代码中每行前有不同数量的空格,这不是编写程序所必需的,但为了使代码更美观,以及使代码与代码之间更能体现其层级关系,使用空格是有其价值的。

【相关知识说明】

(1)Intersect:返回一个Range对象,该对象表示两个或多个区域重叠的矩形区域。本例中两个区域分别为ActiveCell.EntireColumn(表示当前列)和ActiveCell.CurrentRegion(表示当前单元格所在区域,当前区域是以空行与空列的组合为边界的区域),所以Intersect (ActiveCell.EntireColumn, ActiveCell.CurrentRegion)则表示当前列的已用区域,排除空白区。也许以图片来表示这个区域可以更形象化,让读者更易于理解Intersect的用法。

如图1.7所示,当前单元格(ActiveCell)为C4;当前列(ActiveCell.EntireColumn)是C列,即双线框之内的区域;当前单元格所在的已用区域(ActiveCell.CurrentRegion)是单线框之内的区域B2∶E6;而当前列与当前区域的重叠区域Intersect(ActiveCell. EntireColumn, ActiveCell.CurrentRegion)则是C2∶C6,即图中灰色底纹的区域。

图1.7 Intersect示意图

(2)For Each…Next:这是一种循环语句,针对一个数组或集合中的每个元素,重复执行一组语句。本例中将区域中每一个值与C列最大值进行比较,若不相等则继续比较下一个单元格,直到找到目标时停止循环。

(3)WorksheetFunction.Max:VBA中没有直接求最大值的函数,但Excel工作表函数中有MAX可求最大值。在VBA中则可以通过WorksheetFunction前缀来调用工作表函数。

(4)Dim:声明变量(变量:命名的存储位置与数据范围,包含在程序执行阶段可修改的数据。变量名在其声明范围内必须只有唯一名称不可重复。)并分配存储空间,每一个变量都需要声明方可使用。声明变量时除指定变量名称外,还会指定变量类型,不同类型占用空间不同,运行速度也不相同。当在过程中使用Dim语句时,通常将Dim语句放在过程的开始处。当然,在程序中不用Dim语句声明变量,程序也会执行,但速度会慢很多。用户需要养成声明所有变量的习惯。

(5)在过程中使用变量时一般需要先声明其名称和储存空间。如“Dim aa as byte”,其中Dim是声明变量的语句,“aa”表示变量名称,“byte”即变量的储存空间或称范围。用Dim语句声明变量时可以同时声明多个变量。如“dim a as byte,b as intger”,此语句声明了两个变量,在第二个变量处不需要再用Dim前缀。本例中声明了两个变量,类型为单元格对象。

提示

VBA中可以调用大部分工作表函数,只要前缀WorksheetFunction加点后即可列出可在VBA中使用的工作表函数,如图1.8所示。并非所有工作表函数都可以在VBA中使用,如Concatenate。

图1.8 VBA中调用工作表函数

实例4 选择负数单元格

【技巧说明】 一次性选择A1∶D13区域中所有负数所在的单元格。

【案例介绍】 如图1.9所示,奖惩表存在正数和负数。本例利用单元格循环,逐个检测数值,最后一次选定所有负数所在的单元格。

图1.9 奖惩表数据

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码:

Sub选择所有负数单元格()
Dim rng As Range, rg As Range
For Each rng In Range("a1:d13")
If rng < 0 Then
  If rg Is Nothing Then
    Set rg=rng
  Else
    Set rg=Application.Union(rg, rng)
  End If
End If
Next
rg.Select
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,可以看到所有负数据单元格已被选中,其背景呈灰暗效果,如图1.10所示。

图1.10 选中负数后的奖惩表

提示

本实例参见光盘样本:..\第1部分\实例4.xlsm。

【相关知识说明】

Application.Union:返回两个或多个区域的合并区域,支持30个参数。本例中它将查找到的多个负数所在单元格地址合并为一个区域,最后一次选择所有负数区域。

实例5 选择单元格所在区域及工作表已用区域

【技巧说明】 选择单元格所在区域及工作表已用区域。

【案例介绍】 已用区域也称为当前区域,是指以空行与空列的组合为边界的区域。本例中将演示当前单元格区域和当前工作表区域之异同。案例数据车间员工分组表如图1.11所示。

图1.11 车间员工分组表

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码:

Sub选择已用区域()
ActiveCell.CurrentRegion.Select
MsgBox "已选择单元格所在区域。", 64, "提示"
ActiveSheet.UsedRange.Select
MsgBox "已选择本工作表已用区域。", 52, "提示"
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 单元格定位于D1∶E11中任意单元格,使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮。

[6] 程序执行时将弹出一个提示窗口,如图1.12所示,同时B组成员列表之区域D1∶E11已被选中。

图1.12 已选择单元格所在区域

图1.13 已选择当前表已用区域

[7] 单击“确定”按钮后再次弹出一个窗口,如图1.13所示,同时A1:H11区域已被选中。

提示

本实例参见光盘样本:..\第1部分\实例5.xlsm。

【相关知识说明】

(1)CurrentRegion:返回一个Range对象,该对象表示当前区域,本例中表示当前单元格所在区域D1∶E11,其他两个区域因中间有一个空白区而被分隔开。

(2)ActiveSheet.UsedRange:返回一个Range对象,该对象表示指定工作表上所使用的区域,以使用区域的最大行、最大列为边界。

(3)MsgBox:在对话框中显示消息,等待用户单击按钮,并返回一个Integer告诉用户单击哪一个按钮。本函数一般用于告知用户程序在执行中取得的值或者用以暂时中断程序的执行,本例作用为后者。MsgBox函数参数如下:

MsgBox(prompt[, buttons] [, title] [, helpfile, context])

其中,[buttons]参数表示显示按钮的数目及形式,使用的图标样式,默认按钮是什么,以及消息框的强制回应等。本例中第一个消息框显示了一个按钮和消息提示图标;第二个消息框显示了两个按钮和一个三角惊叹号图标。这两项都由[buttons]参数控制,使用该参数时可以用常数,也可以使用值。[buttons]参数列表如下(见表1.2)。

表1.2 MsgBox之buttons参数列表

提示

MsgBox之buttons参数可以用表1.2中各参数值相加产生信息按钮与图标的组合。例如:使用参数65,可产生OK及Cancel两个按钮及一个Information Message图标,即1+64;使用参数259将产生是、否及取消三个按钮,默认按钮为第二个,参数259为3+256而得出。

实例6 选择数组公式区域

【技巧说明】 选择当前单元格所在的多单元格数组公式区域。

【案例介绍】 如图1.14所示,工作表定义了一个名称“星期”,其引用为数组公式={"星期一";"星期二";"星期三";"星期四";"星期五";"星期六";"星期天"},在工作表中输入多单元格数组公式时因错误地多选择了一个单元格,使公式结果产生一个错误值。而数组公式是不可以单独修改其中某单元格的数据的,如删除A9则出错,如图1.15所示。此时就需要先选中整个数组区域才可以进行下一步操作。

图1.14 数组公式结果

图1.15 修改数组公式时出错

【案例实现】 选中数组区域之步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码。

Sub选择数组区域()
    ActiveCell.CurrentArray.Select
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 将鼠标定位于单元格A9,使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,数组公式单元格区域A2∶A9已被选中,如图1.16所示。

图1.16 已选中的数据区域

提示

本实例参见光盘样本:..\第1部分\实例6.xlsm。

【相关知识说明】

ActiveCell.CurrentArray:表示当前单元格所在的数组区域。

实例7 返回单元格合集与交集

【技巧说明】 选择两个区域之合集及两个重叠区域之交集。

【案例介绍】 如图1.17所示,数据分别为“原料仓”、“零用品仓”、“成品仓”三个仓库数据区,同时选择“原料仓”区域A3∶F5及“成品仓”区域A9∶F12则为单元格合集;选中“零用品仓”区域A6∶F8及“入仓”数据列之重叠区域E6∶E8即为单元格交集。

图1.17 仓库进出表

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码:

Sub合集与交集()
Application.Union(Range("A3:F5"), Range("A9:F12")).Select
MsgBox "两个区域的合集已选中。", 64, "提示"
Application.Intersect([a6:f8], Columns("E:E")).Select
MsgBox "两个区域的交集已选中。", 64, "提示"
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,将弹出消息窗口,同时单元格合集已选中,如图1.18所示。

[6] 单击“确定”按钮后将弹出下一个消息框,同时单元格交集已选中,如图1.19所示。

图1.18 选择合集

图1.19 选择交集

提示

本实例参见光盘样本:..\第1部分\实例7.xlsm。

【相关知识说明】

(1)Application.Union:返回两个或多个区域的合并区域。

(2)Application.Intersect:该对象表示两个或多个区域重叠的矩形区域。

(3)[a6:f8]:这是range("a6:f8")的另一种写法,作用相同。

实例8 选择背景色为黄色的单元格

【技巧说明】 选择背景色为黄色的单元格。

【案例介绍】 公司接单表中为了区分下单企业所在城市,将每一个城市的企业下单数据以不同颜色设置背景色,假设广州方向的订单取消需要清除资料时,则需要先选中黄色背景数据所在行。

图1.20 以颜色区分下单企业的接单表

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码:

Sub选择黄色区域()
Dim rng As Range, rg As Range          '声明变量
For Each rng In ActiveSheet.UsedRange    '进入循环
If rng.Interior.Color=65535 Then     '检查背景色是否为黄色
  If rg Is Nothing Then
    Set rg=rng
  Else
    Set rg=Application.Union(rg, rng) '将黄色背景单元格合并为一个单元格合集
  End If
End If
Next                                  '检查下一个
rg.Select                             '选择黄色背景区域
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,可以看到所有黄色背景之单元格已被选中,如图1.21所示。

图1.21 选择所有黄色背景之单元格

提示

本实例参见光盘样本:..\第1部分\实例8.xlsm。

【相关知识说明】

(range).Interior.Color:表示(单元格)内部颜色。也可以用RGB(0,0,0)形式表示。例如,以下代码将单元格A5背景色设置为红色(RGB三个参数都是0~255的阿拉伯数字表示):

Sub单元格颜色()
[a5].Interior.Color=RGB(255, 0, 0)
End Sub

实例9 选择字体为蓝色之单元格

【技巧说明】 选择字体为蓝色之单元格。

【案例介绍】 以实例8数据为基准,假设该接单表不是使用背景色,而是以字体色区分下单企业所在城市,如图1.22所示。

图1.22 以字体色区分下单企业的接单表

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码:

Sub选择蓝色字体区域()
Dim rng As Range, rg As Range      '声明变量
For Each rng In ActiveSheet.UsedRange '进入循环
If rng.Font.ColorIndex=5 Then    '检查字体色是否为蓝色
  If rg Is Nothing Then
    Set rg=rng
  Else
  Set rg=Application.Union(rg, rng) '将字体色为蓝色单元格合并为一个单元格合集
  End If
End If
Next                              '检查下一个
 rg.Select                        '选择蓝色字体区域
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,可以看到所有蓝色字体色之单元格已被选中,如图1.23所示。

图1.23 选择所有蓝色字体色之单元格

提示

本实例参见光盘样本:..\第1部分\实例9.xlsm。

【相关知识说明】

(range).Font.ColorIndex:表示(单元格)字体颜色地址,可用1~56表示。可以用以下代码列出所有颜色地址对应的颜色:

Sub颜色()
    Dim i As Byte
    For i=1 To 56
      Cells(i, 1)="ColorIndex" & i
      Cells(i, 2).Interior.ColorIndex=i
    Next
End Sub

实例10 选择粗线边框之单元格

【技巧说明】 选择当前表已用区域中粗线边框之单元格。

【案例介绍】 如图1.24所示之成绩表,表中部分单元格边框为虚线,部分为加粗实线,加粗实线边框表示未及格人员成绩,现需选择所有未及格成绩的单元格。

图1.24 成绩表

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码:

Sub选择粗线边框之单元格()
    On Error Resume Next
    Dim rng As Range, rg As Range
    For Each rng In ActiveSheet.UsedRange
        If rng.Borders(xlEdgeRight).Weight=xlMedium And rng.Borders
          (xlEdgeTop).Weight=xlMedium _
        And rng.Borders(xlEdgeBottom).Weight=xlMedium And rng.Borders
          (xlEdgeLeft).Weight=xlMedium Then
        If rg Is Nothing Then
          Set rg=rng
        Else
          Set rg=Application.Union(rg, rng)
        End If
    End If
Next
rg.Select
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,可以看到所有加粗实线边框之单元格已被选中,如图1.25所示。

图1.25 选择所有加粗实线边框之单元格

提示

本实例参见光盘样本:..\第1部分\实例10.xlsm。

【相关知识说明】

(1)Borders.Weight:指定某一区域周围边框的宽度。

Borders有一个参数表示方向,xlEdgeRight表示单元格的右边框;xlEdgeTop、xlEdgeBottom、xlEdgeLeft则分别表示上边框、下边框和左边框。

(2)xlMedium:表示单元格边框的粗细,共有4种可选值,本例中为中等粗细。具体见表1.3。

表1.3 表示边框粗细的4种可选值

(3)On Error Resume Next:当程序错误时继续运行下句代码。本例中最后一步是选择带有粗线边框的单元格,假设在指定区域中不存在粗线边框的单元格,则程序运行到此句时要出错,加上“On Error Resume Next”则可以跳过错误。

实例11 反向选择工作表

【技巧说明】 选择当前已选择区域以外的区域。

【案例介绍】 资源管理器中有反向选择,可以选择已选文件以外的所有文件;Excel区域(必须是多单元格)中也可反向选择。如图1.26所示,已选中B组成员之区域D1∶E11,而反向区域则是A1∶H11中排除D1∶E11的区域。

图1.26 已选中B组成员区域

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码:

Sub反向选择()
    Application.DisplayAlerts=False          '禁用警告提示
    Application.ScreenUpdating=False         '禁止屏幕更新
    Dim raddress As String, taddress As String  '声明变量
    raddress=Selection.Address
    taddress=ActiveSheet.UsedRange.Address
    With Sheets.Add                        '添加一个新工作表
      .Range(taddress)=0                    '对新表赋值
      .Range(raddress)="=0"                  '对新表赋值
      raddress=.Range(taddress).SpecialCells(xlCellTypeConstants,
            1).Address '重新设置raddress为含有常量的单元格地址
      .Delete                               '删除新工作表
    End With
    ActiveSheet.Range(raddress).Select         '反向区域选择
    Application.ScreenUpdating=True          '开启屏幕更新
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 选中B组成员之区域D1∶E11,使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,可以看到选中区域以外的单元格已被选中,如图1.27所示。

图1.27 反向选择后的区域

提示

本实例参见光盘样本:..\第1部分\实例11.xlsm。

【相关知识说明】

(1)DisplayAlerts:如果宏运行时Microsoft Excel显示特定的警告和消息,则该属性值为True。Boolean类型,可读写。本例中作用为删除工作表时不弹出警告消息框。

(2)ScreenUpdating:如果启用屏幕更新,则该属性值为True。Boolean类型,可读写。本例中程序运行前将之设为False,即关闭屏幕更新,可以加快程序运行,在程序完毕后恢复更新。

(3)Sheets.Add:新建一个工作表。

(4)Range.SpecialCells:返回一个Range对象,该对象代表与指定类型和值匹配的所有单元格。本例中xlCellTypeConstants参数表示函数有常量的单元格。

实例12 选择单元格区域但排除首行标题

【技巧说明】 选择当前表已用区域但排除首行标题。

【案例介绍】 以实例11的数据为例,首行为标题行A1∶H1,若需要对正文区A2∶H11(标题以外的区域)进行排序、背景标示等,则都需要先选择标首除外的区域。

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码:

Sub排除标题行()
Application.Intersect(ActiveSheet.UsedRange, ActiveSheet.UsedRange.
    Offset(1, 0)).Select
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,可以看到标题行以外的区域已被选中,如图1.28所示。

图1.28 选择标题行以外的区域

提示

本实例参见光盘样本:..\第1部分\实例12.xlsm。

实例13 每隔三行选一行

【技巧说明】 将当前表已用区域每隔三行选一行。

【案例介绍】 如图1.29所示之简易工资表,其中行数为3的N次方的单元格存放的是员工薪资,现需要为薪资行添加背景以突出显示,则需每隔三行选择一行。

图1.29 简易工资表

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码:

Sub隔三行选一行()
    Dim rng As Range, i As Long
    Application.ScreenUpdating=False      '关闭屏幕刷新
    i=ActiveSheet.UsedRange.Rows.Count     '计算已用行数
    With Range("XFD1:XFD" & i)               '在最末列输入公式作为辅助区
      .Formula="=if(mod(row(),3),1,0/0)"  '列号为除以3余数为1时显示1
                                              '否则显示一个0/0的错误值
      Set rng=.SpecialCells(xlCellTypeFormulas, 16).EntireRow
                                              '参数16表示错误值
      rng.Select                           '选择目标行
      .Value=""                          '清空输入区数据
    End With
    Application.ScreenUpdating=True        '恢复屏幕更新
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,可以看到行号为3的N次方的行已被选中,如图1.30所示。

图1.30 每隔三行选一行

提示

本实例参见光盘样本:..\第1部分\实例13.xlsm。

【相关知识说明】

(1)Range.Formula:即在单元格中输入公式,本例中公式为“=if(mod(row (),3),1,0/0)”。

(2)SpecialCells(xlCellTypeFormulas, 16):表示包含错误值的所有单元格。

(3)EntireRow:表示整行,如[a3]. EntireRowg表示第3行。

实例14 选择奇数列

【技巧说明】 选择当前表已用区域之奇数列。

【案例介绍】 如图1.31所示之员工资料表,其中奇数列存放员工姓名,现需提取员工姓名,则需先选中奇数列并排除首行之数据。

图1.31 员工资料表

【案例实现】 操作步骤如下:

[1] 使用快捷键Alt+F11进入VBE(Visual Basic Editor)环境。

[2] 单击菜单【插入】\【模块】,打开模块代码窗口。

[3] 在右边代码窗口输入以下代码:

Sub选择奇数列()
    Dim rng As Range, rang As Range, i As Long
    Application.ScreenUpdating=False         '关闭屏幕刷新
    i=ActiveSheet.UsedRange.Columns.Count     '计算已用列数
    Set rang=ActiveSheet.UsedRange
    With Range(Range("A1048576"), Cells(1048576, i))
'在最末行输入公式作为辅助区
      .Formula="=if(mod(column(),2),0/0,1)"
'列号为除以2余数为1时显示一个0/0的错误值,否则显示1
      Set rng=.SpecialCells(xlCellTypeFormulas, 16).EntireColumn
'参数16表示错误值
      Application.Intersect(rng, rang, rang.Offset(1, 0)).Select
'选择目标列与已用区域的交集
      .Value=""                        '清空输入区数据
    End With
    Application.ScreenUpdating=True        '恢复屏幕更新
End Sub

[4] 关闭VBE窗口返回到工作表。

[5] 使用快捷键Alt+F8调出运行宏窗口,然后单击“执行”按钮,可以看到所有姓名已被选中,可以随意粘贴至其他区域,如图1.32所示。

图1.32 选择奇数列且排除标题

提示

本实例参见光盘样本:..\第1部分\实例14.xlsm。