Sub Statement (Visual Basic)
Declares the name, parameters, and code that define a Sub
procedure.
Syntax
[ <attributelist> ] [ Partial ] [ accessmodifier ] [ proceduremodifiers ] [ Shared ] [ Shadows ] [ Async ]
Sub name [ (Of typeparamlist) ] [ (parameterlist) ] [ Implements implementslist | Handles eventlist ]
[ statements ]
[ Exit Sub ]
[ statements ]
End Sub
Parts
attributelist
Optional. See Attribute List.
Partial
Optional. Indicates definition of a partial method. See Partial Methods.
accessmodifier
Optional. Can be one of the following:
proceduremodifiers
Optional. Can be one of the following:
MustOverride Overrides
NotOverridable Overrides
Shared
Optional. See Shared.
Shadows
Optional. See Shadows.
Async
Optional. See Async.
name
Required. Name of the procedure. See Declared Element Names. To create a constructor procedure for a class, set the name of a
Sub
procedure to theNew
keyword. For more information, see Object Lifetime: How Objects Are Created and Destroyed.typeparamlist
Optional. List of type parameters for a generic procedure. See Type List.
parameterlist
Optional. List of local variable names representing the parameters of this procedure. See Parameter List.
Implements
Optional. Indicates that this procedure implements one or more
Sub
procedures, each one defined in an interface implemented by this procedure's containing class or structure. See Implements Statement.implementslist
Required if
Implements
is supplied. List ofSub
procedures being implemented.implementedprocedure [ , implementedprocedure ... ]
Each
implementedprocedure
has the following syntax and parts:interface.definedname
Part Description interface
Required. Name of an interface implemented by this procedure's containing class or structure. definedname
Required. Name by which the procedure is defined in interface
.Handles
Optional. Indicates that this procedure can handle one or more specific events. See Handles.
eventlist
Required if
Handles
is supplied. List of events this procedure handles.eventspecifier [ , eventspecifier ... ]
Each
eventspecifier
has the following syntax and parts:eventvariable.event
Part Description eventvariable
Required. Object variable declared with the data type of the class or structure that raises the event. event
Required. Name of the event this procedure handles. statements
Optional. Block of statements to run within this procedure.
End Sub
Terminates the definition of this procedure.
Remarks
All executable code must be inside a procedure. Use a Sub
procedure when you don't want to return a value to the calling code. Use a Function
procedure when you want to return a value.
Defining a Sub Procedure
You can define a Sub
procedure only at the module level. The declaration context for a sub procedure must, therefore, be a class, a structure, a module, or an interface and can't be a source file, a namespace, a procedure, or a block. For more information, see Declaration Contexts and Default Access Levels.
Sub
procedures default to public access. You can adjust their access levels by using the access modifiers.
If the procedure uses the Implements
keyword, the containing class or structure must have an Implements
statement that immediately follows its Class
or Structure
statement. The Implements
statement must include each interface that's specified in implementslist
. However, the name by which an interface defines the Sub
(in definedname
) doesn't have to match the name of this procedure (in name
).
Returning from a Sub Procedure
When a Sub
procedure returns to the calling code, execution continues with the statement after the statement that called it.
The following example shows a return from a Sub
procedure.
Sub mySub(ByVal q As String)
Return
End Sub
The Exit Sub
and Return
statements cause an immediate exit from a Sub
procedure. Any number of Exit Sub
and Return
statements can appear anywhere in the procedure, and you can mix Exit Sub
and Return
statements.
Calling a Sub Procedure
You call a Sub
procedure by using the procedure name in a statement and then following that name with its argument list in parentheses. You can omit the parentheses only if you don't supply any arguments. However, your code is more readable if you always include the parentheses.
A Sub
procedure and a Function
procedure can have parameters and perform a series of statements. However, a Function
procedure returns a value, and a Sub
procedure doesn't. Therefore, you can't use a Sub
procedure in an expression.
You can use the Call
keyword when you call a Sub
procedure, but that keyword isn't recommended for most uses. For more information, see Call Statement.
Visual Basic sometimes rearranges arithmetic expressions to increase internal efficiency. For that reason, if your argument list includes expressions that call other procedures, you shouldn't assume that those expressions will be called in a particular order.
Async Sub Procedures
By using the Async feature, you can invoke asynchronous functions without using explicit callbacks or manually splitting your code across multiple functions or lambda expressions.
If you mark a procedure with the Async modifier, you can use the Await operator in the procedure. When control reaches an Await
expression in the Async
procedure, control returns to the caller, and progress in the procedure is suspended until the awaited task completes. When the task is complete, execution can resume in the procedure.
Note
An Async
procedure returns to the caller when either the first awaited object that’s not yet complete is encountered or the end of the Async
procedure is reached, whichever occurs first.
You can also mark a Function Statement with the Async
modifier. An Async
function can have a return type of Task<TResult> or Task. An example later in this topic shows an Async
function that has a return type of Task<TResult>.
Async
Sub
procedures are primarily used for event handlers, where a value can't be returned. An Async
Sub
procedure can't be awaited, and the caller of an Async
Sub
procedure can't catch exceptions that the Sub
procedure throws.
An Async
procedure can't declare any ByRef parameters.
For more information about Async
procedures, see Asynchronous Programming with Async and Await, Control Flow in Async Programs, and Async Return Types.
Example 1
The following example uses the Sub
statement to define the name, parameters, and code that form the body of a Sub
procedure.
Sub ComputeArea(ByVal length As Double, ByVal width As Double)
' Declare local variable.
Dim area As Double
If length = 0 Or width = 0 Then
' If either argument = 0 then exit Sub immediately.
Exit Sub
End If
' Calculate area of rectangle.
area = length * width
' Print area to Immediate window.
Debug.WriteLine(area)
End Sub
Example 2
In the following example, DelayAsync
is an Async
Function
that has a return type of Task<TResult>. DelayAsync
has a Return
statement that returns an integer. Therefore, the function declaration of DelayAsync
must have a return type of Task(Of Integer)
. Because the return type is Task(Of Integer)
, the evaluation of the Await
expression in DoSomethingAsync
produces an integer, as the following statement shows: Dim result As Integer = Await delayTask
.
The startButton_Click
procedure is an example of an Async Sub
procedure. Because DoSomethingAsync
is an Async
function, the task for the call to DoSomethingAsync
must be awaited, as the following statement shows: Await DoSomethingAsync()
. The startButton_Click
Sub
procedure must be defined with the Async
modifier because it has an Await
expression.
' Imports System.Diagnostics
' Imports System.Threading.Tasks
' This Click event is marked with the Async modifier.
Private Async Sub startButton_Click(sender As Object, e As RoutedEventArgs) Handles startButton.Click
Await DoSomethingAsync()
End Sub
Private Async Function DoSomethingAsync() As Task
Dim delayTask As Task(Of Integer) = DelayAsync()
Dim result As Integer = Await delayTask
' The previous two statements may be combined into
' the following statement.
' Dim result As Integer = Await DelayAsync()
Debug.WriteLine("Result: " & result)
End Function
Private Async Function DelayAsync() As Task(Of Integer)
Await Task.Delay(100)
Return 5
End Function
' Output:
' Result: 5