Excelの醍醐味! 明日からできるデータの並べ替え、検索、置換、抽出:Excelマクロ/VBAで始める業務自動化プログラミング入門(7)(2/5 ページ)
プログラミング初心者を対象にExcelマクロ/VBAを使った業務自動化プログラムの作り方を一から解説します。今回は、データ操作のメソッド、Sort、Find、FindNext、Replace、AutoFilter、AdvancedFilterなどの使い方について、実例を交えて解説する【Windows 10、Excel 2016に対応】。
データの検索
図3のような表があり、「読みを入力」に「読み」を入力して「実行」ボタンをクリックすると、その「読み」に該当するセルが選択されるマクロを書いてみよう。「実行」ボタンはExcelメニューの[挿入]→[図形]から作成している。
Findメソッドの使い方
セルに入力されているデータを検索するには、Findメソッドを使用する。書式は下記の通りだ(参考「Range.Find Method(Excel)- MSDN」)。
Findメソッドの書式
Rangeオブジェクト.Find(What:={What},LookIn:={LookIn},LookAt:={LookAt})
- 「What」には検索するデータを指定(必須)
- 「LookIn」には検索対象の種類を表7から指定(オプション)
- 「LookAt」には「完全一致」または「部分一致」かを表8から指定(オプション)
設定値 | 説明 |
---|---|
xlFormulas | 数式 |
xlValues | 値 |
xlComments | コメント |
設定値 | 説明 |
---|---|
xlWhole | 完全一致 |
xlPart | 部分一致 |
表の検索を行ってみよう
マクロはリスト2のようになる。「読みを入力」の欄に入力された「読み」を、完全一致検索で行う。
Sub 検索() Range("D8:D17").Find(What:=Range("C4").Value, LookAt:=xlWhole).Select End Sub
図3の「実行」ボタンを選択して、マウスの右クリックで表示されるメニューから[マクロの登録]を選択する。[マクロ登録]の画面が表示されるので、「検索」を選択して[OK]ボタンをクリックする。これで、「実行」ボタンにマクロが登録された。
では、「C4」のセルに「読み」を平仮名で入力して「実行」ボタンをクリックしてみよう。図4のように該当するセルが選択されるはずだ。
データの検索と条件分岐の組み合わせで、データがなかった場合の処理
では、指定した「読み」のデータが見つからなかった場合はどうするか。プログラムでは、このようなデータがなかった場合の処理を書くことが非常に大切だ。データがなかった場合は「該当データがありません!」と表示させる心遣いが必要だ。その記述方法を解説しよう。
データがなかった場合のマクロはリスト3のように書く。
Sub 検索() Dim result As Range Set result = Range("D8:D17").Find(What:=Range("C4").Value, LookAt:=xlWhole) If result Is Nothing = False Then result.Select Else MsgBox "該当データがありません!" Exit Sub End If End Sub
2〜3行目でRange型のオブジェクト変数「result」を宣言し、検索結果をresult変数にSetステートメントで格納する。
4〜9行目では、「If〜Else〜End If」ステートメントで条件分岐を行っているが、この構文については前回の「If〜Thenによる二者択一の条件分岐」「Elseで指定した条件以外の処理」などを参照してほしい。
データがある(データがない状態ではない)場合(4行目)は、そのセルを選択し(5行目)、ない場合(6行目)はMsgBox関数でメッセージを表示する(7行目)。MsgBox関数については、後の連載で解説する。
実行結果は図5のようになる。
FindNextメソッドと繰り返し処理の組み合わせで自動化
次に、同性同名の人物があった場合はどうするかを考えてみよう。膨大なデータの中には当然同姓同名の人物も存在する可能性は100%ある。そのような場合、全ての人物を選択する処理を書いてみよう。
FindNextメソッドの使い方
このような場合の処理にはFindNextメソッドを使用する。書式は下記の通りだ。
FindNextメソッドの書式
Rangeオブジェクト.FindNext({After})
引数{After}は省略可能で、セルの場所を指定する。指定したセルの次のセルから検索が開始される。
FindNextメソッドを使うマクロはリスト4のように記述する。
Option Explicit Sub 同姓同名検索() Dim firstFindCell As Range Dim firstCell As Range Dim result As Range Set firstFindCell = Range("D8:D20").Find(What:=Range("C4").Value, LookAt:=xlWhole) Set firstCell = firstFindCell Set result = firstFindCell Do Set firstFindCell = Range("D8:D20").FindNext(firstFindCell) If firstFindCell.Address = firstCell.Address Then Exit Do Else Set result = Union(result, firstFindCell) End If Loop result.Select End Sub
最初に見つかったデータを格納するRangeオブジェクト変数「firstFindCell」と、最初に見つかったデータを保持しておくための変数「firstCel」、結果を格納するRangeオブジェクト変数「result」を宣言する(3〜5行目)。
「読みを入力」で入力された平仮名の「読み」を完全一致で検索し(7行目)、最初に見つかったセルのデータをfirstCellにセットしておく(8行目)。resultにも最初に見つかったセルのデータfirstFindCellの値をセットしておく(9行目)。
「Exit Do」で繰り返し処理から抜ける
Do〜Loopで繰り返し処理を行う(11〜18行目)。この構文については前回の「条件が成立している間、処理を繰り返すDo While〜Loop」を参照してほしい。ここでは、繰り返しを終了する条件の「While」を使っていない。「Exit Do」ステートメントで繰り返し処理から抜けることになる(14行目)。
セルD8〜D20の範囲のセル内を、FindNextメソッドで、最初に見つかったデータを保持しているfirstFindCellの値で検索していく(12行目)。
最初に見つかったデータのアドレスと、次のデータのアドレスが同じの場合、つまりデータが1個しかない場合(13行目)は、それのみを選択して、繰り返し処理を抜ける(14行目)。
セル範囲を集約するUnionメソッドの使い方
それ以外は、Unionメソッドでresultのセル範囲とfirstFindCell範囲を、1つのRangeオブジェクトに集約して返す(16行目)。この場合は変数resultに検索結果のセル範囲が集約してセットされる。
Unionメソッドの書式は下記の通り。第1引数と第2引数は必須だ。
Unionメソッドの書式
Set {Rangeオブジェクト変数}=Union({セル範囲1},{セル範囲2}、……)
実行結果
最後にSelectメソッドで該当するデータを全て選択する(19行目)。
実行すると、図19のようになる。
Copyright © ITmedia, Inc. All Rights Reserved.
関連記事
- Excelマクロ/VBAリファレンス用途別・キーワード別一覧超まとめ
- ピボットテーブルとは何か──「そもそも、何をする機能か」を理解する
Excelを通じて「ピボットテーブル」の基礎を学び、データ分析を実践するまでを習得する本連載。初回はピボットテーブルの基礎と、「どんなことができるのか」を解説する。 - どんなビジネスにも欠かせないリレーショナルデータベースの基礎知識と作り方――テーブル、レコード、フィールド、主キーとは
Accessを通じて、初心者がリレーショナルデータベースやSQLの基本を学び、データベースを使った簡単なシステムの作り方を習得する本連載。初回はデータベースの基本を理解し、Accessを使い始めてみよう。