Click here to Skip to main content
15,867,568 members
Articles / Programming Languages / Visual Basic
Tip/Trick

Call Functions Until One Meets Condition

Rate me:
Please Sign up or sign in to vote.
5.00/5 (16 votes)
1 May 2012CPOL1 min read 45.8K   17   16
Call a series of functions until the return value meets a condition without a chained-if or short-circuiting.

Thanks to cechode for inspiring this tip/trick. Suppose you have the following functions:

C#
bool Step1()
{
    return true;
}
bool Step2(int val1, int val2)
{
    return val1 == val2;
}
bool Step3()
{
    MessageBox.Show("I will be reached.");
    return false;
}
bool Step4()
{
    throw new Exception("This should be impossible!");
}
VB.NET
Function Step1() As Boolean
    Return True
End Function

Function Step2(ByVal val1 As Integer, ByVal val2 As Integer) As Boolean
    Return val1 = val2
End Function

Function Step3() As Boolean
    MessageBox.Show("I will be reached.")
    Return False
End Function

Function Step4() As Boolean
    Throw New Exception("This should be impossible!")
End Function

If you want to execute each of those in sequence until one returns false, you can do the following:

C#
new Func<bool>[]
{
    Step1,
    // You can use a lambda to wrap a function with a different signature.
    () => Step2(1, 1),
    Step3,
    Step4,
    // You can use a lambda to avoid the use of a function.
    () => 0 == 1
}.Any((step) => !step());
VB.NET
' This is achieved fairly easily in VB.NET
Select Case False
    Case Step1()
    Case Step2(1, 1)
    Case Step3()
    Case Step4()
    Case 0 = 1
End Select

Note that the result need not be true or false; it can be any value or condition. I could, for example, process each function until the result is an integer greater than or equal to 5 (Note that in VB.NET the Select Case statement can't handle conditions, it can only handle values, so the code is modified accordingly):

C#
// This assumes each "Step" function from above returns an int rather than a bool.
new Func<int>[]
{
    Step1,
    () => Step2(1, 1),
    Step3,
    Step4,
    () => 0 + 1
}.Any((step) => step() >= 5);
VB.NET
' VB.NET.
Dim steps() As Func(Of Integer) =
{
    AddressOf Step1,
    Function() Step2(1, 1),
    AddressOf Step3,
    AddressOf Step4,
    Function() 0 + 1
}
 
' We test against a condition rather than a value.
steps.Any(Function([step]) [step]() >= 5)

The condition >= 5 is a very short one, so this won't save you any typing over the short-circuiting technique shown below. However, it would save you some typing for longer conditions. Specifying the condition only once rather than for each value also reduces the probability that you will make a mistake when typing. And if you change the condition later on, you only have to change the condition in one place rather than many. Here is the short-circuiting approach, which leads to duplicated code:

C#
// Don't do this.
if (Step1() >= 5 ||
    Step2(1, 1) >= 5 ||
    Step3() >= 5 ||
    Step4() >= 5 ||
    0 + 1 >= 5)
{ }
VB.NET
' VB.NET. Don't do this.
If Step1() >= 5 OrElse
Step2(1, 1) >= 5 OrElse
Step3() >= 5 OrElse
Step4() >= 5 OrElse
0 + 1 >= 5 Then
End If

While shorter for this example (due to the short condition), this code also has the maintenance problems and higher probability of human error explained above.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Web Developer
United States United States

  • Managing Your JavaScript Library in ASP.NET (if you work with ASP.net and you don't read that, you are dead to me).
  • Graduated summa cum laude with a BS in Computer Science.
  • Wrote some articles and some tips.
  • DDR ("New high score? What does that mean? Did I break it?"), ping pong, and volleyball enthusiast.
  • Software I have donated to (you should too):

Comments and Discussions

 
GeneralMy vote of 5 Pin
Pravin Patil, Mumbai26-Jun-12 21:02
Pravin Patil, Mumbai26-Jun-12 21:02 
QuestionVery nice trick Pin
zenwalker19857-Jun-12 5:37
zenwalker19857-Jun-12 5:37 
GeneralMy vote of 5 Pin
thatraja1-May-12 18:52
professionalthatraja1-May-12 18:52 
GeneralRe: Definitely makes more sense if you are doing an operation th... Pin
Andrew Rissing30-Mar-11 3:42
Andrew Rissing30-Mar-11 3:42 
GeneralRe: Done updating. Pin
AspDotNetDev29-Mar-11 10:05
protectorAspDotNetDev29-Mar-11 10:05 
GeneralRe: Cool, I'll let you know once I'm finished making updates. I ... Pin
AspDotNetDev29-Mar-11 6:26
protectorAspDotNetDev29-Mar-11 6:26 
GeneralRe: I'll keep an eye out for the update, because at this point I... Pin
Andrew Rissing29-Mar-11 5:46
Andrew Rissing29-Mar-11 5:46 
GeneralReason for my vote of 5 Makes you think, and then you are go... Pin
FDW23-Jun-11 23:57
FDW23-Jun-11 23:57 
Reason for my vote of 5
Makes you think, and then you are going to like it.
Generalhow do i move my alternate from a pending state? ( been like... Pin
cechode29-Mar-11 4:33
cechode29-Mar-11 4:33 
GeneralRe: It requires approval from another person. Looks like somebod... Pin
AspDotNetDev29-Mar-11 6:25
protectorAspDotNetDev29-Mar-11 6:25 
GeneralI agree with Jose. While interesting academically, what is ... Pin
Andrew Rissing29-Mar-11 4:01
Andrew Rissing29-Mar-11 4:01 
GeneralRe: Good question. This version can compare against more than ju... Pin
AspDotNetDev29-Mar-11 4:28
protectorAspDotNetDev29-Mar-11 4:28 
GeneralRe: I agree with Jose. While interesting academically, what is ... Pin
frankazoid1-May-12 12:17
frankazoid1-May-12 12:17 
GeneralI like the aproach...... but, I supose: bool ret= Step1() ... Pin
Jose David Pujo28-Mar-11 23:48
Jose David Pujo28-Mar-11 23:48 
GeneralRe: FYI, I updated the tip/trick to show how this goes beyond sh... Pin
AspDotNetDev29-Mar-11 11:41
protectorAspDotNetDev29-Mar-11 11:41 
GeneralReason for my vote of 5 Great snippet. Pin
Aamir Butt28-Mar-11 23:18
Aamir Butt28-Mar-11 23:18 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.