Visual Basic.NET Short Circuit Demo

Wrapping up our week of short circuit posts, we have the Visual Basic.NET short circuit demo. If you are fluent in C# this will look shockingly familiar. I just translated between the two languages what I did in the C# version. We will explore the same ground so if you understand the C#, you might not get much more than the first two posts on short circuiting. For the rest, here is the Visual Basic.NET short circuit demo.

Just like before, this is a Windows Forms program called ShortCircuitingVB. It has a button called Button1 and a listbox called lbTest1.

Visual Basic .NET Short Circuit demo Form1.vb

Imports System.Threading
 
Public Class Form1
    Private Sub Button1_Click(sender As Object, e As EventArgsHandles Button1.Click
        test_LDFirst()
        test_LDLast()
 
        lbTest1.Items.Clear()
 
        lbTest1.Items.Add("Long Wait Function First " + AvgTest1().ToString())
        lbTest1.Items.Add("Long Wait Function Last " + AvgTest2().ToString())
    End Sub
 
    Private Function AvgTest1() As Double
        Dim diff As List(Of TimeSpan) = New List(Of TimeSpan)()
        Dim totalMS As Double = 0
 
        For i As Integer = 0 To 100
            diff.Add(test_LDFirst())
        Next
 
        For i As Integer = 0 To 100
            totalMS = diff(i).TotalMilliseconds * 1000
        Next
 
        totalMS /= 100
 
        Return totalMS
    End Function
 
    Private Function AvgTest2() As Double
        Dim diff As List(Of TimeSpan) = New List(Of TimeSpan)()
        Dim totalMS As Double = 0
 
        For i As Integer = 0 To 100
            diff.Add(test_LDLast())
        Next
 
        For i As Integer = 0 To 100
            totalMS = diff(i).TotalMilliseconds * 1000
        Next
 
        totalMS /= 100
 
        Return totalMS
    End Function
 
    Private Function test_LDFirst()
        Dim results As TimeSpan
        Dim test As Stopwatch = New Stopwatch()
        Dim value = False
 
        test.Start()
 
        If (longDelay() AndAlso value = TrueThen
            test.Stop()
        Else
            test.Stop()
        End If
 
        results = New TimeSpan(test.ElapsedTicks)
 
        Return results
    End Function
 
    Private Function test_LDLast()
        Dim results As TimeSpan
        Dim test As Stopwatch = New Stopwatch()
        Dim value = False
 
        test.Start()
 
        If (value = True AndAlso longDelay()) Then
            test.Stop()
        Else
            test.Stop()
        End If
 
        results = New TimeSpan(test.ElapsedTicks)
 
        Return results
    End Function
 
    Private Function longDelay()
        Thread.Sleep(1)
        Return True
    End Function
End Class

longDelay()

Unlike the C# example we will go bottom up rather than top down. Give this post a different perspective than the last.

This function represents something that is resource intensive. It causes a long delay and returns true. We never want it to cause our short circuit to fail. It would mess up my example if it fails. We want the easy thing to fail, not the hard.

test_LDFirst() and test_LDLast()

In these functions, we will do the exact same thing. Well almost. In one we call the long delay first in our conditional and the other we call it last.

This function starts with a TimeSpan to return the time between starting and ending the test. We have the test stopwatch that is the actual time keeper. Finally we have the value which forces our condition to fail by being false.

With all the declarations out of the way, we start the test then do the short circuit evaluation. When it completes, we stop it. Both paths will stop it but the success will never happen. I have it there to make Intellisense happy.

Finally we store the results of the stopwatch in results and return it to the calling function.

AvgTest1 and AvgTest2

In these nearly identical functions we want to take an average of 100 tests so that we can eliminate any noise that might happen in 1 test.

We start with a list of Timespans to store the results of each of the 100 tests. We then run the 100 tests. AvgTest1 tests having the long delay as the first evaluated condition while AvgTest2 evaluates it second. Once the tests are done, we focus on the average. We take a sum of all the tests then multiple each result by a 1000 to make it more intelligible to people. When the sum is built we take that divide by 100 to get the average and return the results.

Button 1 Click Event

Finally we get to the click event that will run each test once because the first test is slower then the rest of the runs. My best guess on why is that the IL has something being loaded lazily and it need to instantiate a bunch of stuff on that first call.

We clear out any previous results in the listbox and add the two calls for the two averages and show them in the results listbox.

Lets see what it looks like.

Like the C# example, this is roughly 20 units. Both code bases should compile into very similar code so we should get similar results. I can already hear from the C# people, that this is not true see the VB.NET is slower. It just happened this set of test was slower because there was less local resources available. Another run looks like this.

Visual Basic Short Circuit Example, which has the first long delay at about 20 and the last at about 0.001 units

Lets force both conditional to evaluate

To force both conditions to evaluate we need to swap the AndAlso for an And. If we were using an or statement, it would be Or getting swapped for OrElse.

Visual Basic .Net Short Circuit Demo minus the short circuit

Imports System.Threading
 
Public Class Form1
    Private Sub Button1_Click(sender As Object, e As EventArgsHandles Button1.Click
        test_LDFirst()
        test_LDLast()
 
        lbTest1.Items.Clear()
 
        lbTest1.Items.Add("Long Wait Function First " + AvgTest1().ToString())
        lbTest1.Items.Add("Long Wait Function Last " + AvgTest2().ToString())
    End Sub
 
    Private Function AvgTest1() As Double
        Dim diff As List(Of TimeSpan) = New List(Of TimeSpan)()
        Dim totalMS As Double = 0
 
        For i As Integer = 0 To 100
            diff.Add(test_LDFirst())
        Next
 
        For i As Integer = 0 To 100
            totalMS = diff(i).TotalMilliseconds * 1000
        Next
 
        totalMS /= 100
 
        Return totalMS
    End Function
 
    Private Function AvgTest2() As Double
        Dim diff As List(Of TimeSpan) = New List(Of TimeSpan)()
        Dim totalMS As Double = 0
 
        For i As Integer = 0 To 100
            diff.Add(test_LDLast())
        Next
 
        For i As Integer = 0 To 100
            totalMS = diff(i).TotalMilliseconds * 1000
        Next
 
        totalMS /= 100
 
        Return totalMS
    End Function
 
    Private Function test_LDFirst()
        Dim results As TimeSpan
        Dim test As Stopwatch = New Stopwatch()
        Dim value = False
 
        test.Start()
 
        If (longDelay() And value = TrueThen
            test.Stop()
        Else
            test.Stop()
        End If
 
        results = New TimeSpan(test.ElapsedTicks)
 
        Return results
    End Function
 
    Private Function test_LDLast()
        Dim results As TimeSpan
        Dim test As Stopwatch = New Stopwatch()
        Dim value = False
 
        test.Start()
 
        If (value = True And longDelay()) Then
            test.Stop()
        Else
            test.Stop()
        End If
 
        results = New TimeSpan(test.ElapsedTicks)
 
        Return results
    End Function
 
    Private Function longDelay()
        Thread.Sleep(1)
        Return True
    End Function
End Class

Lets compile and see what trouble we got ourselves into.

Visual Basic Short Circuit Example Minus Short Circuits, which has both at about 20.

Both evaluate just like our short circuit with the long delay first. All three evaluated all conditions so it is not surprising we get similar results.

Hopefully, these three posts on short circuiting make this topic a bunch clearer for folks. I have not seen many good examples about short circuit programming in general and even less about in the Visual Basic .NET community. Let me know if this helped you down in the comments below.

Leave a Reply

Your email address will not be published. Required fields are marked *