第07ラウンド VBAエキスパート・ベーシック試験対策もかねたクイズR07

Excel VBAエキスパート・ベーシック試験対策も兼ねたクイズ

VBAエキスパートの問題集が少なくて、困っている方のために
ベーシック試験対策もかねたクイズを作成しました。

VBAエキスパートへの道クイズ【第13回】REE

クイズ13回に登場した語句の解説

語句の解説はクイズの下にあります。


VBAエキスパートへの道クイズ13回に登場した問題と語句の解説

VBA関数に関する問題

人気外国人俳優のリストが全角で入力されている。 これを半角に変換するにはどのようなVBA関数を使ってコードを書けば良いか?
解説: テキストを全角から半角へ変換するにはStrConv関数をつかいます。
01番の図

StrConv関数は文字列をある形式から別の形式へ変換するときに便利です。例えば、StrConv関数にvbNarrowを引数として与えると、全角文字を半角文字に変換することができます。
問題で提示されたコードの、For Each Rng In Selectionループは選択された各セルに対して同じ操作を行うために使われます。
このケースで適切なのは選択肢1のStrConv関数です。
02番の図


Sub 全角To半角()
    Dim Rng As Range
    For Each Rng In Selection
        Rng.Value = StrConv(Rng.Value, vbNarrow) ' 全角を半角に変換する
    Next Rng
End Sub

セル A 1 から A 3に Format 関数を使って 日付の書式を設定した。 画像のように表示させるためにはコードをどのように書いたら良いか。同じくなるコードを選べ。
解説: Excel VBAでFormat関数を使用すると、日付や数値を特定の書式に従って表示することができます。
03番の図
Format関数は、この関数は第一引数に書式を適用したい値(この場合は現在の日付と時刻を返すNow関数)、第二引数にはその書式を文字列で指定します。
Range("A1").Value = Format(Now, "ggge年")では、和暦の年号と年を表示します。
Range("A2").Value = Format(Now, "m/d日(aaaa)")では、月/日の形式に続けて曜日を全角括弧内に表示します。
ここでmは月を1桁または2桁で(必要ならば)、dは日を1桁または2桁で、aaaaは曜日を完全な名前で表示します。
Range("A3").Value = Format(Now, "yy年m月d日(aaaa)")では、年は最後の2桁のみ、月と日は1桁または2桁で、曜日を全角括弧内に完全な名前で表示します。

次のマクロを実行した時、 A 1セルに入る文字列はどれか。 正しいものを答えなさい。

Sub 文字列操作()
    Dim sta As String
    sta = "  一二三四五六七八九十 "
    Range("A1").Value = Mid(LTrim(sta), 3, 4)
End Sub

解説: このVBAの問題は文字列の操作を行う問題です。
使用されているLTrim関数は、文字列の左端にあるすべての空白を削除します。
そしてMid関数は、第一引数に与えられた文字列から、第二引数で指定した位置から始まる、第三引数で指定した数の文字を返します。
sta変数には" 一二三四五六七八九十 "という文字列が代入されており、文字列の前には2つの空白が含まれています。
LTrim(sta)は、先頭の空白を取り除き、"一二三四五六七八九十"という文字列になります。
その後、Mid関数によりこの文字列の3文字目から4文字分を取り出す操作を行います。
文字列"一二三四五六七八九十"において3文字目は"三"です。そこから4文字を取り出すと"三四五六"になります。
従って、Range("A1").Value = Mid(LTrim(sta), 3, 4)
のコードにより、A1セルに"三四五六"という文字列を代入します。

Sheet2をコピーしてその後ろにコピーしたシートを配置します。シートの指定方法で正しいものは、どれですか?
解説:
04番の図

別ブックにコピーするケース。原本シートをコピーして、あらかじめ開いている”覚書.xlsx”ブックの先頭に移動するマクロを作成しました。どのコードが正しいですか?
解説: 原本シートを別のブックの先頭に移動するマクロについての問題です。
05番の図
それぞれのコードを見てみましょう。
ThisWorkbook.Activateは現在のブック(マクロを含んでいるブック)をアクティブにします。
その後、Worksheets("原本").Move before:=Workbooks(myBook).Worksheets(1)は
"原本"という名前のワークシートを変数myBookで参照されるブックの最初のワークシートの前に移動します。
ここでのmyBookは変数であり、その値が"覚書.xlsx"という文字列であることが、提供されたコードによって示されています。
次に、Workbook(myBook).Worksheets(1)には誤りがあります。
WorkbookではなくWorkbooksというコレクションを使う必要があります。
また、before =となっている部分はbefore:=であるべきです。
別の選択肢ではMove before:=myBook.Worksheets(1)となっていますが、これは構文が間違っています。
myBookは文字列の変数であり、Workbooksコレクションの一部として扱われるべきです。

選択したシートを一番右に移動するプロシージャで、どのブックで実行しても同じ結果が得られるコードはどれですか?
解説: 問題の意図は、どのExcelブックにおいても同じ効果を持つコードを選ぶということです。
06番の図
ActiveSheet.Move After:=Sheets(Sheets.Count)
これは現在選択されているシートを、ブック内のシートの数に基づいて最後の位置に移動させるコードです。
Sheets.Countはブック内のシートの総数を返しますので、これを使用して最後のシートの後ろに移動するという命令になります。
ブックのシート数が変わってもこのコードは常に最後のシートの位置に移動させるため、どのブックにおいても同じ結果を得ることができると言えます。従って、これが正解です。
ActiveSheet.Move After:=Worksheets("千葉支店")
このコードは現在選択されているシートを、名前が"千葉支店"のシートの後ろに移動させます。
しかし、このコードが正しく動作するためには、ブックに"千葉支店"という名前のシートが存在している必要があります。
もしその名前のシートがなければエラーになります。ブックによっては存在しない可能性があるので、このコードはどのブックでも同じ結果を得るためのコードとは言えません。
ActiveSheet.Move Before:=Worksheets(4)
このコードは現在選択されているシートを、4番目のシートの前に移動させます。しかし、すべてのブックにおいて4番目のシートが存在するとは限りません。
正解は、ActiveSheet.Move After:=Sheets(Sheets.Count) です。
このプロシージャは任意のブックに対して実行可能であり、ブック内のシートの数が異なる場合でも適応可能です。

選択シートをコピーして、末尾に追加して名前を変更するマクロを作成しました。 どのブックで実行しても同じ結果を得られるコードはどれですか?
解説: 質問のポイントは、「どのワークブックでも」同じ結果を得られるという点です。
07番の図
選択されたシートをコピーし、ワークブックの最後に追加し、そのシートの名前を「山梨支店」と変更する必要があります。

Sub 末尾にコピーし名前を変更()
    ActiveSheet.Copy After:=Worksheets(Worksheets.Count)
    Worksheets(Worksheets.Count).Name = "山梨支店"
End Sub

このコードはActiveSheetを使っており、これは現在アクティブ(選択されている)シートを意味するので、どのシートが選択されているかに依存せずに機能します。
また、Worksheets.Countを使用しているため、どんなワークブックであってもシートの総数を取得し、最後にシートを追加することができます。

Sub 末尾にコピーし名前を変更()
    Worksheets("原本").Copy After:=Worksheets(4)
    Worksheets(Worksheets.Count).Name = "山梨支店"
End Sub

このコードは特定のシート名 "原本" とシートのインデックス 4 を指定しています。 そのため、"原本" シートが存在しない、またはワークシートの数が4ではないワークブックでは、予期せぬ結果やエラーが発生する可能性があります。

Sub 末尾にコピーし名前を変更()
    Worksheets("原本").Copy After:=Worksheets("千葉支店")
    Worksheets(Worksheets.Count).Name = "山梨支店"
End Sub

こちらも特定のシート名 "原本" と "千葉支店" を指定しているため、これらのシートが存在しない場合には機能しません。

新規ブックを追加して、 A 1セルに”追加”と書き、ブックに名前をつけてブックを閉じるコードを記述しました。 正しい コードはどれですか?
解説: Close Savechanges:=True かFalseか
08番の図

With Workbooks.Add
    .Worksheets(1).Range("A1").Value = "追加!"
    .SaveAs ThisWorkbook.Path & "\追加.xlsx"
    .Close Savechanges:=True
End With

コードは、新規のワークブックを作成し、A1セルに文字列"追加!"を入力してから、現在のワークブックのパスに"追加.xlsx"として保存し、最後に変更を保存してワークブックを閉じます。
この流れは問題文の要件に合っています。
上記コードが正解です。

With Workbooks.Add
    .SaveAs ThisWorkbook.Path & "\追加.xlsx"
    .Worksheets(1).Range("A1").Value = "追加!"
    .Close Savechanges:=False
End With

このコードでは、新規ワークブックに名前を付けて保存した後にA1セルに値を入れています。これは問題文の順序と異なります。また、SaveChanges:=False とすることで、A1セルに入力した値が保存されずにブックが閉じられてしまいます。

With Workbooks.Add
    .SaveAs ThisWorkbook.Path & "\追加.xlsx"
    .Worksheets(1).Range("A1").Value = "追加!"
End With
Workbooks("追加.xlsx").Close Savechanges:=False

このコードは、新規ワークブックを保存後に値を入力していますが、最後にSavechanges:=False を使ってワークブックを閉じるため、A1セルの変更が保存されずに失われます。これも問題文の要件を満たしていません。