wrote :: 2005.12.15

トップページ > Excel > VBA > 講座:セルの操作 > セルのコピー

セルのコピー

■マクロ記録の落とし穴

マクロによるセルのコピーは、ビギナーとベテランで最も差が出るコードのひとつです。たとえば、セルA1をセルC2にコピーするコードを考えてみましょう。この操作をマクロ記録すると、次のようなコードが生成されます。

Sub Macro1()
    Range("A1").Select
    Selection.Copy
    Range("C2").Select
    ActiveSheet.Paste
End Sub

なるほど、確かに間違っていませんが、決して美しいコードではありません。このコードを参考にして、Sheet1のセルA1をSheet2のセルC2にコピーするコードを作ってみましょう。おそらく次のようになると思います。

Sub Sample1()
    Worksheets("Sheet1").Select
    Range("A1").Select
    Selection.Copy
    Worksheets("Sheet2").Select
    Range("C2").Select
    ActiveSheet.Paste
    Worksheets("Sheet1").Select
End Sub

Selectの多用は速度的に不利ですし、画面が切り替わるのもわずらわしいです。そもそも、セルをコピーするのに「コピー元を選択」→「選択セルをコピー」→「コピー先を選択」→「選択シートに貼り付け」という手順がナンセンスです。マクロ記録は操作を忠実にコード化しますから、決して最適化されたコードを生成しないという良い例ですね。

マクロ記録で得られたコードを見て、「そうか、セルのコピーはCopyを使うのか」とわかったら、すぐにヘルプで確認しなければいけません。Copyは何オブジェクトのメソッドだろう?Copyに引数はないのだろうか?など、マクロ記録のコードからはわからないからです。こうした好奇心を持つことが、VBAマスターへも第一歩なのです。ちなみにヘルプは日本語で書かれています。「わかりにくい」と嘆くより「わかろう」と努力してください。さて、ヘルプでCopyメソッドを調べると、次のような構文が書かれています。

expression.Copy(Destination)

expression   必ず指定します。対象となるRangeオブジェクトを返すオブジェクト式を指定します。
Destination  省略可能です。バリアント型(Variant)の値を使用します。コピー先のセル範囲を指定します。
             この引数を省略すると、クリップボードへコピーされます。

expressionは、要するにコピー元です。Selection.Copyとか、Range("A1").Copyのように書けという意味です。それより気になるのは引数Destinationです。解説によると、コピー先のセルを指定します と書かれています。そう、Copyメソッドは、コピー元をクリップボードにコピーするだけでなく、同時にコピー先を指定することもできるのです。
マクロ記録で生成されたコードでは、Copyメソッドの引数Destinationが省略されていますので、解説の通りコピー元はクリップボードへコピーされます。そこで次のコードとして、貼り付けのPasteメソッドが必要になってくるのです。
とはいえ、マクロ記録を責めてはいけません。マクロ記録は、行われた操作を忠実にコード化しただけなのですから。

では、ベテランはどう書くかというと、Copyメソッドの引数Destinationにコピー先を指定して、次のようにスッキリしたコードを使います。

Sub Sample2()
    Range("A1").Copy Range("C2")
End Sub

もし、Sheet1のセルA1からSheet2のセルC2にコピーする場合も、

Sub Sample3()
    Worksheets("Sheet1").Range("A1").Copy Worksheets("Sheet2").Range("C2")
End Sub

これで終わりです。
コードが少ないので高速ですし、修正が容易ですし、ミスが減りますし、可読性が高いですし…良いことばかりです。

■もっと簡単にコピー

Copyメソッドは、セル全体をコピーします。セル内のデータだけでなく、セルに設定されている書式も含めてセル全体です。ところが、セルをコピーするとき「データだけでいいんだけど…」というときもあるでしょう。そんなときは、律儀にCopyメソッドを使わず、次のようにする手もあります。

Sub Sample4()
    Range("C2") = Range("A1")
End Sub

書式は引き継がれませんが、セルのデータはコピーできます。これで十分なケースも多いはずです。


[表示形式の設定]戻る← | →進む[セル範囲の取得]