Findを使って特定の文字列が入っているセルを見つけることができます。
別のファイルから特定の項目を見つけて、さらに別のファイルにコピペする際に便利です。
Findで文字列を検索する
Findの使い方
以下のデータの中から、”測定値A”のセルの位置を取得しましょう。
Sub test()
target = Rows(1).Find("測定値A")
MsgBox target
End Sub
検索範囲を指定してから、Find(“検索文字”)と書きます。
もし検索範囲内に指定の文字が存在すれば、変数targetに検索した文字が入ります。
実行してみて”測定値A”が表示されれば成功です。
行番号or列番号を取得する方法
Sub test()
r = Rows(1).Find("測定値A").Row
c = Rows(1).Find("測定値A").Column
MsgBox r
MsgBox c
End Sub
行番号が欲しければRow、列番号ならColumnをつけ足せば番号が手に入ります。
ただし、列の場合はアルファベットじゃなくて番号になるので注意しましょう。
検索範囲を広げる方法
Sub test()
r = Range(Rows(1), Rows(2)).Find("測定値A").Row
c = Range(Rows(1), Rows(2)).Find("測定値A").Column
MsgBox r
MsgBox c
End Sub
上記コードは1,2行目の中から”測定値A”を探します。
Range(Rows(), Rows())で複数行を対象に指定可能です。
例えば3~5行を対象にしたいなら、Range(Rows(3), Rows(5))にしましょう。
また、Cellsを使えばシート全体を指定できます。
Sub test()
r = Cells.Find("測定値A").Row
MsgBox r
End Sub
ただし全体を検索範囲にすると、欲しくない位置を取得する可能性も高まります。
完全一致 or 部分一致にする方法
Sub test()
c = Rows(1).Find("測定値", LookAt:=xlPart).Column
MsgBox c
End Sub
引数LookAtを設定すると”完全一致”か”部分一致”かを選べます。
上記コードは部分一致にしているので”測定値”が含まれればヒットします。
xlWholeにすると完全一致ですが、今回は”測定値”という項目がありません。
そのため実行すると下図のようなエラーになります。
複数のセルが条件に当てはまる場合
Sub test()
c = Rows(1).Find("測定値", LookAt:=xlPart).Column
MsgBox c
End Sub
複数のセルが条件に当てはまる場合は最も番号の若いセルがヒットします。
例えば上記コードの場合、”測定値”が含まれれば条件を満たします。
つまり”測定値A,B,C”のどれでも当てはまります。
しかし実行すると2が表示されるはずです。
つまり、この方法では”測定値A”しかヒットしません。
すべての”測定値”が欲しい場合はFindNextを使いましょう。
FindNextで複数の文字を検索する
FindNextの使い方
Sub test()
target1 = Rows(1).Find("測定値", LookAt:=xlPart).Column
target2 = Rows(1).FindNext(Rows(1).Find("測定値", LookAt:=xlPart)).Column
MsgBox target1
MsgBox target2
End Sub
まず変数target1では、Findで1つ目の”測定値”を見つけます。
そしてFindNextの()に1行目で使ったFindをそのまま入れてください。
実行するとtarget1は2をtarget2は3を表示するはずです。
このようにFindNextなら複数ヒットしたセルを順番に取り出すことができます。
Findを変数に格納する方法
Sub test()
Dim target As Range
Set target = Rows(1).Find("測定値", LookAt:=xlPart)
col1 = target.Column
col2 = Rows(1).FindNext(target).Column
MsgBox col1
MsgBox col2
End Sub
同じコードを何度も書き続けると面倒なので、Setを使ってまとめましょう。
Dimで変数targetがセルの位置であることを定義します。
Setで変数targetが最初に見つけたセルであると決めましょう。
するとFindNextにはtargetと入れるだけで済みます。
3つ以上のセルをヒットさせる方法
“測定値A” ~ “測定値C”の3つを取得してみましょう。
Sub test()
Dim target As Range
Set target = Rows(1).Find("測定値", LookAt:=xlPart)
col1 = target.Column
col2 = Rows(1).FindNext(target).Column
Set target = Rows(1).FindNext(target)
col3 = Rows(1).FindNext(target).Column
MsgBox col1
MsgBox col2
MsgBox col3
End Sub
“測定値A” ~ “測定値Cの列番号を”col1” ~ “col3″として取得しました。
検索対象が見つかったら、それを変数targetとし、さらに次を探していきます。
ちなみに、下記コードのように更新を忘れると失敗します。
Sub test()
Dim target As Range
Set target = Rows(1).Find("測定値", LookAt:=xlPart)
col1 = target.Column
col2 = Rows(1).FindNext(target).Column
col3 = Rows(1).FindNext(target).Column
MsgBox col1
MsgBox col2
MsgBox col3
End Sub
targetは常に1個目のデータを指すので、col2もcol3も同じデータがヒットしているためです。
なので、検索対象が見つかったら必ず更新するようにしましょう。
loopで複数のセルを検索する
Sub test()
Dim target As Range
Set target = Rows(1).Find("測定値", LookAt:=xlPart)
i = 1
Do While i < 4
MsgBox target.Column
Set target = Rows(1).FindNext(target)
i = i + 1
Loop
End Sub
同じ処理を何度も書くのはめんどくさいので、loop文で繰り返しましょう。
Do~Loopまでの処理が繰り返されます。
3回で終わりなので条件はWhile i < 4です。
loop文の中でtargetを更新しているので、実行されるたびに次の”測定値”を探してくれます。
FindNextの無限ループ
Sub test()
Dim target As Range
Set target = Rows(1).Find("測定値", LookAt:=xlPart)
Start = target.Address
Do
MsgBox target.Column
Set target = Rows(1).FindNext(target)
If target.Address = Start Then
Exit Do
End If
Loop
End Sub
FindNextでは、一通りすべてのデータを見つけた後に1個目のデータに戻ってきます。
ここで、変数Startをつまり”測定値A”の位置として保存しましょう。
そして、loop文の中でもしtargetの位置がStartと同じなら、処理を終えるようにします。
すると、1周処理が終わってStartに戻ってくるタイミングでループを終えてくれます。
まとめ
今回はFindとFindNextを解説しました。
1つだけ見つけたいならFindで、複数見つけたいならFindNextをループさせましょう。
コピペのプログラムと非常に相性が良いのでぜひ使ってみてください!
コメント