Office関連

表の特定の列に対して処理を行うWordマクロ

2015/6/12 追記:
下記で紹介しているコードはセルの結合を考慮していません。
結合されたセルが列内に存在する場合は、新田さんの記事「【Wordマクロ】表の特定の列を選択する」をご参照ください。

Word MVPの新田さんの記事「【Wordマクロ】特定の列のフォント書式を変更する」とExcel MVPの伊藤さんの記事「表の列を選択するWordマクロ」を見て、

“あれ?Wordの表の列に対して何か処理するマクロって流行っているのか!?”

と思った私。
これはもう乗っかるしかない!(勝手に)

何で余計なところまで処理しちゃうの!?

新田さんの記事を読んで気になった点が一点。

Rangeオブジェクトで列を選択したいのですが、1列目だけを排他的に選択することができません。

“いけるんじゃないの?コレくらい!?”

というわけで試してみました。
作業中の文書にあるテーブルの2列目だけを選択するマクロです。

Public Sub Test1()
  Dim r As Word.Range
  
  Set r = ActiveDocument.Tables(1).Rows.First.Cells(2).Range
  r.EndOf wdColumn, wdExtend
  r.Select
End Sub

「ActiveDocument.Tables(1).Columns(2).Select」で済む話なんですが、Rangeオブジェクトを使って処理をするためにわざと上記のようなコードにしています。

このコードを実行すると、

Word_Table_Column_01

上図の通り、ちゃんと2列目だけ選択されます。
ところが、下記のように2列目の文字色を変更するコードになると、

Public Sub Test2()
  Dim r As Word.Range
  
  Set r = ActiveDocument.Tables(1).Rows.First.Cells(2).Range
  r.EndOf wdColumn, wdExtend
  r.Font.ColorIndex = wdRed
End Sub

下図のような結果になります。

Word_Table_Column_02

“なんでやねん!!お前さっきまで2列目だけ選択しとったやろ??”

Wordに対して思わずツッコみ炸裂です。
恐らく下図のようなことなんだと思いますが、正直意味分かりません。

Word_Table_Column_03

だからといって、

Public Sub Test3()
  ActiveDocument.Tables(1).Columns(2).Select
  Selection.Font.ColorIndex = wdRed
End Sub

のようにSelectionを使うのは、何だか負けた気がします。
ここはやはりRangeで攻めるべきです。

Rangeオブジェクトで表中の特定列を処理する

ではどうするか?
表の列を表すColumnオブジェクトからRangeオブジェクトを直接取得できれば良いのですが、残念ながらそれらしいプロパティはありません。

使えそうなのは列中のセルを表す“Cells”コレクション。

Cell“s”が示す通り、セルを表すCellオブジェクトの集まりです。

Cellオブジェクトからは目的のRangeオブジェクトが取得できるので、今回はこれを使うことにします。

Public Sub Test4()
  Dim c As Word.Cell
  
  For Each c In ActiveDocument.Tables(1).Columns(2).Cells
    c.Range.Font.ColorIndex = wdRed
  Next
End Sub

これでようやくSelectを使って選択範囲を変えることなく、表中の特定列に対して処理を行うことができました。
(ループを使うのも何だか負けた気がしますが、この際気にしないでおきます。)

Word_Table_Column_04

で、どっちが早いの?

Selectionで処理するのか、ループしてRangeで処理するのか、結果的に同じであればどちらでも良いわけですが、ここで気になってくるのは“どちらが早く処理できるか?”ということ。

試しに2,000行のテーブルに対して処理を行ってみました。

Private Declare Function timeGetTime Lib "winmm" () As Long

Public Sub Test5()
  Dim tmp As Word.Range
  Dim start As Long
  
  start = timeGetTime()
  Set tmp = Selection.Range
  ActiveDocument.Tables(1).Columns(2).Select
  Selection.Font.ColorIndex = wdRed
  tmp.Select
  Debug.Print "Selectionでの処理時間:" & timeGetTime() - start
End Sub

Public Sub Test6()
  Dim c As Word.Cell
  Dim start As Long
  
  start = timeGetTime()
  For Each c In ActiveDocument.Tables(1).Columns(2).Cells
    c.Range.Font.ColorIndex = wdRed
  Next
  Debug.Print "ループ&Rangeでの処理時間:" & timeGetTime() - start
End Sub

結果は下図の通りで、ループ&Rangeのコードの方が若干時間が掛かりました。
1セルずつ処理しているので、仕方ないと言えば仕方がない結果ですね。

Word_Table_Column_05

Ctrl + Zキー一発で元の状態に戻せることも考えても、Selectionで処理した方が良いのかもしれません。

ただ、“Selectするのは負けだ!”という方は、Rangeで処理することをお薦めいたします。

新しいOutlook.comのプレビュー版を触ってみました。前のページ

[Officeアドイン]メールアドイン(旧メールアプリ)がExchange不要になりました。次のページ

関連記事

  1. Office アドイン

    Office 2016で進化したOffice アドイン

    今日OfficeDevを眺めていて気が付いたのが「OfficeJS S…

  2. Office関連

    空白文字を一括置換するWordマクロ

    様々なWord文書を扱っていると、下図のように“同じ空白のように見えて…

  3. Excel

    漢字かな交じり文をひらがなにするマクロ

    Yahoo!のテキスト解析Web API(ルビ振り)を使用して、漢字か…

  4. Office関連

    [Word VBA]引数の型がVariantになっているのはなぜ?

    インストラクターのネタ帳でお馴染みの伊藤さんが先日下記の記事をアップさ…

  5. アイコン一覧

    Office 2013 アイコン一覧(F)

    ・Office 2013 アイコン一覧 NUM…

コメント

  • コメント (0)

  • トラックバックは利用できません。

  1. この記事へのコメントはありません。

Time limit is exhausted. Please reload CAPTCHA.

※本ページはプロモーションが含まれています。

Translate

最近の記事

アーカイブ

PAGE TOP