限定しりとり

VBAを勉強し始めて1週間ほどになります。
そこで、掲題のエラーが出てしまい、何が原因か分からず途方にくれてます。
掲題のエラーで検索すると、同じようなエラーで悩んでいる人がいますが、
私の事例を解決する案を見つけることが出来ませんでしたので、
今回質問させていただきます。

まず、下記で示すプロシージャとは別のSUBプロシージャで計算し、表を
作成します。表は、計算条件によって行数が変わります。
その表をクリアさせるのに、下記で示すSUBプロシージャを作成しました。

Public Sub 値のクリア()

Dim a_clr As Integer 'A列の縦の値
Dim b_clr As Integer 'B列の縦の値
Dim MaxRow As String '表の最終行を取得
Dim MaxCol As String '表の最終列を取得
MaxRow = Cells(Rows.Count, 4).End(xlUp).Row '表の行の最終行を取得
MaxCol = Cells(7, Columns.Count).End(xlToLeft).Column '表の列の最終列を取得
MsgBox (MaxRow)
MsgBox (MaxCol)
Worksheets("計算").Range("d7", Cells(MaxRow, MaxCol)).ClearContents ← エラーになる。
Worksheets("計算").Range("d7", Cells(MaxRow, 16)).ClearContents    ←問題なく動作します。
End Sub

これを動作させると、掲題のエラーが出ます。
エラーが出る箇所は、Rangeプロパティの行です。
プログラム中にも書いてますが、書き方により動作したり
しなかったりします。

Range("d7", Cells(MaxRow, MaxCol)).ClearContents ← エラーになります。

Range("d7", Cells(MaxRow, 16)).ClearContents    ← 問題なく動作します。

デバッグモードの時に、Cells(MaxRow, MaxCol))の中の変数(MaxRow, MaxCol)にマウス
を持っていくと、数値が表示されます。
その数値は、私が必要としている数値がきちんと入っています。
それなのに、なぜここでとまっているのか分かりません。
また、Cells(MaxRow, MaxCol)をCells(MaxRow, 16)の用に数値にすると
問題なく動作する理由もよく分かりません。
変数の指定の仕方などが悪いのか、今一理解しきれていないのが原因かも
知れませんが、アドバイスをいただけると助かります。

よろしくお願いします。

A 回答 (3件)

excelの変数の扱いはいい加減(良く言えば柔軟)で



Cells("1", 2)

などは、

Cells(1, 2)

に変換してくれると思います。
これはCells(行,列)の行側は必ず数値なので、勝手に変換する(してくれる?)のだけれど、列側は数値の場合の他に"A"や"B"と文字列で指定する場合があると思います。

Cells(1,1)



Cells(1,"A")

ともかけると思います。
なので

Cells(1,"1")

の列側は数値と文字列で全く違う扱いなので、さすがに"1"を勝手には数値化できないのだと思います。
試しに列側の文字列をval関数で数値化する

Worksheets("計算").Range("d7", Cells(MaxRow, Val(MaxCol))).ClearContents

がエラーにならないのはもちろん、列側の文字列に数値の0を加えて

Worksheets("計算").Range("d7", Cells(MaxRow, MaxCol + 0)).ClearContents

としても、文字+数値は数値として扱ってくれるので、エラーにはならないと思います。
ただ、文字列同士の足し算は思わぬ値なので注意が必要だと思います。

Sub sample()
Dim a As Integer
Dim b As Integer
Dim c As String
Dim d As String
a = 1
b = 2
c = "3"
d = "4"

MsgBox a + b ' 1 + 2 = 3 (数値同士なので足し算)
MsgBox c + d ' "3" + "4" = "34" (文字列同士なので、文字列の結合)
MsgBox c + a ' "3" + 1 = 4 '文字列と数値の足し算なので文字列を数値化して足し算

End Sub
    • good
    • 0
この回答へのお礼

なるほど。
そういうことなんですね。
まさに霧が晴れたとはこのことです。
大変ありがとうございます。

VAL関数なども初めて知りました。
試したら問題なく動作すしました。

まだまだ、知らないことばかりですがこれから勉強していきます。

ありがとうございます。

お礼日時:2011/02/18 13:27

困ったときは、眺めてもわからないもの。



今回のは
IF MAXCOL=16 THEN

IF MAXCOL="16" THEN
等して検証
罠を仕掛けるのも手法。

少し見直しで
質問しないでも自己解決できるほうが良い。

定義エラーだから定義もみる。


さらなるデバッグをしてほしい。投稿し回答待っている時間がもったいない。
    • good
    • 0
この回答へのお礼

確かに自己解決できるのが一番よいですね。
もちろんただ眺めていたわけではないです。
今の自分に出来ることや書籍の購入などして調べましたが、はっきりと分かりませんでした。
バリアント型にすれば動作することも確認してますし(実際その状態で使用してました)
Msgboxにて変数に数値が代入されているかなどの確認もしました。
使用に関してはまったく問題なかったのですが、なにぶん気持ち悪かったので、
はっきりとした答えが知りたく思い質問させていただきました。
そういう意味では、回答者(3)さんの回答で霧が晴れた感じです。

なにぶんやり始めて1週間(延べ7~8時間ぐらいの知識)しかないため、
デバッグのやり方や柔軟な解決方法などなかなか思いつきませんでした。

今後も質問させていただく可能性はありますので、その時も忌憚のない意見を
お願いします。

ありがとうございます。

お礼日時:2011/02/18 14:15

> Dim MaxRow As String '表の最終行を取得


> Dim MaxCol As String '表の最終列を取得
どちらも文字列型ではなく数値型で定義してみて下さい。
    • good
    • 0
この回答へのお礼

Dim MaxRow As Integer '表の最終行を取得
Dim MaxCol As Integer '表の最終列を取得

型宣言を変更したら問題なく動作しました。
ありがとうございます。
実は、バリアント型にすれば、動作するのが分かっていたのですが、
数値型にすればよいことは思いつきませんでした。
今一型宣言の意味を理解していませんでしたが、今回のことで、
なんとなく分かった気がします。

ありがとうございました。

お礼日時:2011/02/18 13:22

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!