Methods, Parameters and Scope

6.1 Subs and Functions

Public Sub Log(message As String)
    Console.WriteLine($"[{Date.Now:HH:mm:ss}] {message}")
End Sub

Public Function CalculateTax(amount As Decimal, Optional rate As Decimal = 0.18D) As Decimal
    Return Math.Round(amount * rate, 2, MidpointRounding.AwayFromZero)
End Function

6.2 Parameter Passing

ByVal (default) Copy of the value (or of the reference for classes) Alias of the caller's variable Optional... = default

Caller may omit it (must be a compile-time constant) Variable number of arguments (last parameter) Foo(rate:=0.2D, amount:=100) <Out> attribute Marks ByRef as out for C# interop

Sub Swap(Of T)(ByRef a As T, ByRef b As T)
    Dim t = a : a = b : b = t
End Sub

Function Average(ParamArray values() As Double) As Double
    Return If(values.Length = 0, 0, values.Average())
End Function

Sub Configure(Optional host As String = "localhost", Optional port As Integer = 80)
End Sub
Configure(port:=8080)

6.3 Overloading, Recursion and Local Functions

Overload by parameter count, type, or order. Return type alone isn't enough.

VB has no local functions. Use lambdas assigned to local variables, or private methods.

Function Fib(n As Integer) As Long
    Return If(n < 2, n, Fib(n - 1) + Fib(n - 2))
End Function
Dim memo As New Dictionary(Of Integer, Long)
Dim fibMemo As Func(Of Integer, Long) = Nothing
fibMemo = Function(n)
              If n < 2 Then Return n
              Dim r As Long
              If memo.TryGetValue(n, r) Then Return r
              r = fibMemo(n - 1) + fibMemo(n - 2)
              memo(n) = r
              Return r
          End Function

6.4 Scope, Lifetime and Accessibility

Dim in If/For Dim, Static Protected, Protected Friend, Private Protected Derived types (± assembly)

<Assembly: InternalsVisibleTo("Shop.Tests")> exposes Friend members to a test project.