Excel VBA | 関数の戻り値と ByRef の使い分け — 設計フロー(チェックリスト+コード例)

VBA
スポンサーリンク

初心者が「戻り値」と「ByRef」をどう使い分けるか迷わないように、設計判断フローをチェックリスト形式で整理しました。各ステップに対応するコード例も付けています。


設計チェックリスト

  1. 返す値は1つだけか?
    • ✔ Yes → 関数の戻り値で返す
    • ✔ No → 次へ
  2. 複数値を返す必要があるか?
    • ✔ Yes → ByRefで返却用引数を使う
    • ✔ No → 次へ
  3. 参照(RangeやWorksheetなど)を差し替えたいか?
    • ✔ Yes → ByRefで参照を変更
    • ✔ No → 次へ
  4. 副作用を避けたいか?
    • ✔ Yes → ByVal+戻り値で安全に設計
    • ✔ No → ByRefを使っても良いが、コメントで意図を明示する

コード例付きフロー

1. 値が1つだけ → 戻り値

Function AddTax(ByVal amount As Double) As Double
    AddTax = amount * 1.1
End Function

Sub Test1()
    Debug.Print AddTax(1000)   ' → 1100
End Sub
VB

2. 複数値を返す → ByRef

Sub GetCoordinates(ByRef x As Double, ByRef y As Double)
    x = 10
    y = 20
End Sub

Sub Test2()
    Dim a As Double, b As Double
    GetCoordinates a, b
    Debug.Print a, b   ' → 10, 20
End Sub
VB

3. 参照を差し替える → ByRef

Sub MoveRange(ByRef r As Range)
    Set r = r.Offset(1, 0)
End Sub

Sub Test3()
    Dim rng As Range
    Set rng = Sheet1.Range("A1")
    MoveRange rng
    rng.Value = "Shifted"   ' A2 に書き込まれる
End Sub
VB

4. 副作用を避けたい → ByVal+戻り値

Function GrowArray(ByVal src() As Long, ByVal newSize As Long) As Long()
    Dim b() As Long, i As Long
    ReDim b(1 To newSize)
    For i = LBound(src) To UBound(src)
        b(i) = src(i)
    Next
    GrowArray = b
End Function

Sub Test4()
    Dim a() As Long
    ReDim a(1 To 2): a(1) = 10: a(2) = 20
    a = GrowArray(a, 4)
    Debug.Print UBound(a)   ' → 4
End Sub
VB

✅ まとめ

  • 戻り値は主結果用 → 読みやすく安全。
  • ByRefは副次結果や参照差し替え用 → 意図を明示して使う。
  • 入力は必ずByVal → 呼び出し元を壊さない。
  • コメントや名前付けで意図を明示 → 「返却用」「参照変更用」と分かるように。

👉 このチェックリストを「設計の定規」として使えば、ByRefの危険な副作用を避けつつ、必要な場面でだけ安全に活用できます。

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