達人養成塾 小川です。
今日は、さいきんいただいた質問から。
前回のセミナーのときに、持参したのですがそこで質問する時間がありませんでした。。
初・中級講座で習いました基本の基。シート分割マクロを応用してます。(応用というかほとんど焼きなおしって感じですが。)とても役に立っています。
以前から、もっとスマートな記述方法がないかと、考えたり調べたりテキストをひっくり返しているのですが、どうも今の自分には引っ掛かってきません。
記述方法あるいは、何をどう調べたらいいかお教え頂けますでしょうか。
内容は、添付ファイルの最後のFor ~ Next の間のEnd Ifの後の、
増やしていったシートに大元のデータをコピーする記述です。
shTo.Range(“A” & cTo).Value = shFm.Range(“A” & cFm).Value
↓
shTo.Range(“R” & cTo).Value = shFm.Range(“R” & cFm).Value
A列分からR列分まで、上記のようにずらずらと書いてあります。
[中略]
記述例はどこにも見つかりません。。。
全くのお手上げで、必要な列数分ずらずらコピペを繰り返しています。
列数が限られているときはいいのですが、列数が多くなれば多くなるほど、記述が増えていきます。
ここをもっと簡単に記述する方法はないでしょうか?
現状では、列範囲は全てコピーされても構わない状況です。
お忙しいところ申し訳ありませんが、ご教示のほどよろしくお願いいたします。
ということで、書かれていたマクロは、こんな感じだった。(抜粋)
Sub CreateSheet_RowsB() ‘B列基準でシート分割する。A~R列まで有効
Dim shTo As Worksheet
Dim shFm As Worksheet
Dim cFm As Long
Dim cTo As Long
Dim cFmMx As Long
‘[中略]
Set shFm = Worksheets(“Sheet1”) ‘基本シート名は「Sheet1」であること
cFmMx = shFm.Range(“C65536”).End(xlUp).row
For cFm = 2 To cFmMx ‘2行目から最終行まで
‘[中略]
‘[課題の箇所ここから]
shTo.Range(“A” & cTo).Value = shFm.Range(“A” & cFm).Value
shTo.Range(“B” & cTo).Value = shFm.Range(“B” & cFm).Value
shTo.Range(“C” & cTo).Value = shFm.Range(“C” & cFm).Value
shTo.Range(“D” & cTo).Value = shFm.Range(“D” & cFm).Value
shTo.Range(“E” & cTo).Value = shFm.Range(“E” & cFm).Value
shTo.Range(“F” & cTo).Value = shFm.Range(“F” & cFm).Value
shTo.Range(“G” & cTo).Value = shFm.Range(“G” & cFm).Value
shTo.Range(“H” & cTo).Value = shFm.Range(“H” & cFm).Value
shTo.Range(“I” & cTo).Value = shFm.Range(“I” & cFm).Value
shTo.Range(“J” & cTo).Value = shFm.Range(“J” & cFm).Value
shTo.Range(“K” & cTo).Value = shFm.Range(“K” & cFm).Value
shTo.Range(“L” & cTo).Value = shFm.Range(“L” & cFm).Value
shTo.Range(“M” & cTo).Value = shFm.Range(“M” & cFm).Value
shTo.Range(“N” & cTo).Value = shFm.Range(“N” & cFm).Value
shTo.Range(“O” & cTo).Value = shFm.Range(“O” & cFm).Value
shTo.Range(“P” & cTo).Value = shFm.Range(“P” & cFm).Value
shTo.Range(“Q” & cTo).Value = shFm.Range(“Q” & cFm).Value
shTo.Range(“R” & cTo).Value = shFm.Range(“R” & cFm).Value
‘[課題の箇所ここまで]
cTo = cTo + 1
Next
‘[中略]
End Sub
ということで、コメント。
まず、「あるシート上のあるセルの値を別のシートの別のセルに転記する」というような機能のマクロを作る場合。
「自動記録をしながら値をコピーして、それを使いまわす」というのはいただけない。
shTo.Range(“R” & cTo).Value = shFm.Range(“R” & cFm).Value
のような感じで、.Value プロパティを取得し、そして、とってきた値をそのまま設定するのがスマート。
そして、今回の質問の件。
課題となっていた箇所は、どうやって簡潔に書くか。
↓答えは、こんな感じ。
Sub CreateSheet_RowsB() ‘B列基準でシート分割する。A~R列まで有効
Dim shTo As Worksheet
Dim shFm As Worksheet
Dim cFm As Long
Dim cTo As Long
Dim cFmMx As Long
‘[中略]
Set shFm = Worksheets(“Sheet1”) ‘基本シート名は「Sheet1」であること
cFmMx = shFm.Range(“C65536”).End(xlUp).row
For cFm = 2 To cFmMx ‘2行目から最終行まで
‘[中略]
‘[↓]こんな感じになる。
shTo.Range(“A” & cTo & “:R” & cTo).Value = shFm.Range(“A” & cFm & “:R” & cFm).Value
cTo = cTo + 1
Next
‘[中略]
End Sub
ということで、実は、単純な複数セルの値の転記は、実は、一行で済む。
こういうとき、
Range(“A1:C5”) と言ったら、A1からC5までの複数のセルのことを指すということが分かっているかどうかがひとつのミソ。
そうすると、
“A1:C5” という文字列を、
“A” & “1” & “:C” & “5” と分割する発想とか、さらに、変数を活用して、
“A” & cTo & “:C” & cFm
という具合に記述してみようかという発想につながる。
分かってしまえば、「な~んだ ヾ(´ー`)ノ 」という感じだ。
ヾ(´ー`)ノ ヾ(´ー`)ノ ヾ(´ー`)ノ