【コレだけでOK】VBA「Range メソッドは失敗しました:’_Worksheet’オブジェクト」エラー完全ガイド

Excel VBA 入門

「Range メソッドは失敗しました:’_Worksheet’オブジェクト」って出るけどなんなんだ?
昨日までの使えていたのに、急にRangeメソッドエラーで使えなくなった!

VBAを始めた人が一度はハマるエラーがRangeメソッドのエラーです。このエラーは、使うときの状況によって正常に動く場合もあるため、初心者にとってとても厄介なエラーです。実行時エラー’1004’の中の一つですが、VBAに慣れてきた人も引っかかることの多いエラーでもあります。

この記事では、その仕組みから対処法までを丁寧に解説していきます。ぜひこの記事の内容を活用して、効率よくVBAを作成していってください!

またこのブログでは、効率化に関する様々な情報を発信しています。ぜひほかの記事も参考にして、ちょっとした業務を効率化してみてください!

【結論】原因は「親シート不一致」が9割

このエラーの原因のほとんどは「親シートの不一致」によるものです。特に、Rangeの内側でCellsを使うとき、外側と内側で違うシートを参照してしまいこのエラーが出ることが大半です。

外側のRangeと内側のCellsで親がそろわない = 別シートのセルが一つの Range に入っている

という事が起こってしまい、Rangeメソッドは失敗しましたというエラーが発生します。ここからは実際のコードを使って、このエラーについて詳しく解説していきます。

【原因解説】“親シート不一致” とは何か?

エラーを再現する検証コードで全体像をつかむ

まずはエラーの仕組みを確認します。 Sheet1とSheet2というシートがあるエクセルを用意します。

そのうえで以下のコードを Sheet2 を選んで実行すると、Rangeメソッドのエラーが発生します。

Sub Test()
    Dim Sheet1 As Worksheet
    Dim Sheet2 As Worksheet
    
    Set Sheet1 = Worksheets("Sheet1")
    Set Sheet2 = Worksheets("Sheet2")
    
    Sheet1.Range(Cells(1, 2), Cells(3, 4)) = "こんにちは"
 
End Sub

実行結果:

Range メソッドは失敗しました:’_Worksheet’オブジェクト(Run-time error 1004)

今回エラーが発生しているのは、この部分です。

Sheet1.Range(Cells(1, 2), Cells(3, 4)) = "こんにちは"

エラーの原因を理解するためには、シートを明示しない時の処理が重要となります。

アクティブシートに引っ張られる仕組み

VBAでは、親を省略すると ActiveSheet が自動補完されるという仕様があります。そのため CellsRange も、明示しない限りアクティブシートが対象となります。

アクティブシートは選択されているシートの事なので、その時に開いているエクセルシートが自動的に対象範囲になります。

'実行時開いてるシートのA1に「こんにちは」と入力する
Range("A1") = "こんにちは"


'どこを開いていても、Sheet1のA1に「こんにちは」と入力する
Sheet1.Range("A1") = "こんにちは"

この仕様にによって、今回のエラーは発生しています。

検証コードで実際に何が起きているかを分解解説

改めて今回のコードを確認します。

Sheet1.Range(Cells(1, 2), Cells(3, 4)) = "こんにちは"

このコードをSheet2を選択した状態で実行しています。

すなわち、Rangeとその中のCellsの対象シートは次のようになります。

Sheet1.Range(...) → 親は Sheet1
Cells(1, 2) → 親は アクティブシート(ここでは Sheet2)

あえてコードで書くと次のような状態です。

Sheet1.Range(Sheet2.Cells(1, 2), Sheet2.Cells(3, 4)) = "こんにちは"

この状態では、Sheet1の中にあるSheet2のCellの場所を指示していることになります。その為、Excel が「別シート同士を同時に扱えない」為、エラーを返します。

これがRangeメソッドエラーの原因となります。ここからは、対策として2つの方法を紹介します。

【解決策2つ】「Range メソッドは失敗しました」を瞬時に潰す方法

対処法①:すべてに親を書いてそろえる

もっとも単純かつ確実な方法は、RangeCells も 同じ親(ここでは Sheet1)を 全て書くことです。

Sub Test()
    Dim Sheet1 As Worksheet
    Dim Sheet2 As Worksheet
    
    Set Sheet1 = Worksheets("Sheet1")
    Set Sheet2 = Worksheets("Sheet2")
    
    Sheet1.Range(Sheet2.Cells(1, 2), Sheet2.Cells(3, 4)) = "こんにちは"
 
End Sub

これならアクティブシートがどこでもエラーは出ません。 少し手間ですが、直感的に理解しやすいと思いますので、一旦はこの方法でOKです。

対処法②:With ブロック+ドットで安全運用

大量のセル操作が続く場面では With ブロックを使うことをお勧めします。With シートの後にドット (.) を付ければ、ブロック内のはすべて同じ親シートに固定されます。

Sub Test()
    Dim Sheet1 As Worksheet
    Dim Sheet2 As Worksheet
    
    Set Sheet1 = Worksheets("Sheet1")
    Set Sheet2 = Worksheets("Sheet2")
    
    With Sheet1
       .Range(.Cells(1, 2), .Cells(3, 4)) = "こんにちは"
    End With
End Sub

Withを使うと、長い処理でも「どのシートを触っているか」が一目で分かり、 親不一致によるバグを根本から予防できます。

後から編集するときも見やすいため、VBAに慣れてきたら使ってほしい書き方になります。

まとめ

Range メソッドの失敗は、ほとんどが 親シートの食い違い が原因です。 逆に言うと、親シートの明記を徹底するだけで、このエラーが出ることはほとんどなくなります。

このエラーはVBAに慣れてきた中級者も陥りやすいので、この記事の内容を改めて確認して、親シートの明記の徹底を今一度考えてみてください。

今回のトラブル解決のように、ITスキルはあなたの仕事をより効率的にしてくれます。以下の記事では、Kindle Unlimitedで読める業務効率化に役立つ本を厳選して紹介していますので、ぜひこちらも参考にしてみてください!

※この記事を見た方は、こちらの記事もおすすめです!

コメント

タイトルとURLをコピーしました