範囲内の文字列を配列化するFunction
範囲内の各セルの値(文字列)を配列化するFunction
範囲内の文字列の配列化
この間、
特定の文字列のみ狙い撃ちでゴシック体にする
みたいなくそめんどくさい作業に遭遇した。
もちろん、ちゃちゃっとコード書いて瞬殺したんですが、そのときに、
対象の文字なり文字列なりをワークシートに表で作っておいて、Functionで配列化できたら便利なんじゃね?
と思っただけです。
コーディング
次のようなFunctionを作った。
リスト1 標準モジュール
Public Function getValueArray(ByVal targetRange As Range) _ As String() '……(1)' Dim countOfCells As Integer countOfCells = targetRange.Count '……(2)' Dim tmpArray() As String '……(3)' ReDim tmpArray(countOfCells - 1) Dim n As Integer Dim targetCell As Range For Each targetCell In targetRange '……(4)' tmpArray(n) = targetCell.Value n = n + 1 Next getValueArray = tmpArray '……(5)' End Function
まず、(1)の
Public Function getValueArray(ByVal targetRange As Range) As String()
でFunctionの名前と引数、返り値の型を指定。
引数としてセル範囲を与えると、String型の配列を返すFunctionにしている。
(2)の
countOfCells = targetRange.Count
では、引数で渡されたRangeオブジェクト(targetRange)に含まれるセルの個数をCountプロパティを参照して獲得し、変数countOfCellsにぶち込んでいる。
(3)からの2行
Dim tmpArray() As String ReDim tmpArray(countOfCells - 1)
では、String型の配列変数tmpArray()をとりあえず宣言しておき、すかさずReDim。配列の添え字の最大数は、要素数-1なので、「countOfCells - 1」になる。
(4)からの4行
For Each targetCell In targetRange tmpArray(n) = targetCell.Value n = n + 1 Next
では、「For Each ~ Next」を使って引数で渡された範囲の各セルを巡回し、それぞれの値を配列変数tmpArrayにぶち込んでいく。通常の「For ~ Next」と違って、ブロック内で n をインクリメントしておかないとアホな結果になるので注意。
あとは、(5)の
getValueArray = tmpArray
で配列tmpArrayを返り値としてreturnしてやればおk。
使ってみる
こんなふうに範囲を選択して、次のコードで使ってみる。
リスト2 標準モジュール
Public Sub getValueArrayTest() Dim ar() As String ar = getValueArray(Selection) '……(1)' Dim i As Integer For i = 0 To UBound(ar) '……(2)' If ar(i) = "" Then ar(i) = "*" Debug.Print ar(i) Next End Sub
(1)の
ar = getValueArray(Selection)
は、getValueArrayに引数として「Selection」(選択中のセル範囲)を渡し、返り値を配列変数 ar にぶち込む、という意味。配列用の変数名がなげやりですまんw
あとは、(2)からの4行
For i = 0 To UBound(ar) If ar(i) = "" Then ar(i) = "*" Debug.Print ar(i) Next
では、Forループを使って配列 ar の各要素を取り出してイミディエイトに表示するようにしている。UBoundはこういうときに欠かせない組み込み関数ですな。
一応、配列の要素が「""」(長さ0の文字列)だったら代わりに「*」を表示するようにした。
実行結果
このように、「*」が表示されているところを見ると、「For Each ~ Next」では、結合されたセルも一つ一ついわゆる「Zオーダー」で巡回する仕様になっているようだ。
おわりに
使いどころ、他にあるかいな……。あと、Zオーダー以外の順番にも対応する必要があるかも知れん。でもそうなると、Dictionaryでやる方が便利かなあと思ったり。