Introduction
This
is a 'kind of a' Visual Basic alternative to the original tip.
If you want to achieve the same functionality in VB as in the original C# tip, you would have to create a full iterator class. While it could be done, I started to wonder if it is feasible? Writing an iterator class is somewhat painful and maintaining it can also be a pain.
The problem is that Visual Basic doesn't currently have equivalent for yield return command. Visual Studio 2012 will change this but since it's not published yet it's not yet a usable solution.
So, instead of creating an iterator class I ended up to a solution where the extension methods are implented using a C# assembly which is simply referenced from the Visual Basic project. Here's a picture of the project setup.

The CumulativeHelper implemented using C# looks as following:
using System.Linq;
namespace CumulativeHelper {
public static class CumulativeHelper {
public static System.Collections.Generic.IEnumerable<string> CumulativePath(
this System.Collections.Generic.IEnumerable<string> pathPart) {
System.Text.StringBuilder concatenated = new System.Text.StringBuilder();
foreach (string part in pathPart) {
if (concatenated.Length != 0) {
concatenated.Append('\\');
}
concatenated.Append(part);
yield return concatenated.ToString();
}
}
public static System.Collections.Generic.IEnumerable<string> AllButLast(
this System.Collections.Generic.IEnumerable<string> stringItem) {
System.Text.StringBuilder concatenated = new System.Text.StringBuilder();
for (int counter = 0; counter< stringItem.Count() - 1; counter++) {
yield return stringItem.ElementAt(counter);
}
}
public static System.Collections.Generic.IEnumerable<decimal> CumulativeSum(
this System.Collections.Generic.IEnumerable<decimal> numbers) {
decimal summedNumber = 0;
foreach (decimal number in numbers) {
summedNumber = summedNumber + number;
yield return summedNumber;
}
}
}
}
The functionality is described in the original tip.
Calling from Visual Basic
So the code above handles the LINQ iteration. The Visual Basic project has a project reference to the C# assembly so the VB code can call the functionality. The code for the Visual Basic portion looks like this
Imports CumulativeHelper
Module MainModule
Sub Main()
Dim numbers As Decimal() = New Decimal() {1, 3, 5, 7, 11}
System.Diagnostics.Debug.WriteLine("The cumulative sum contains the following results")
For Each partialSum As Decimal In numbers.CumulativeSum()
System.Diagnostics.Debug.WriteLine(" - {0}", partialSum)
Next
System.Diagnostics.Debug.WriteLine("The cumulative sum total is {0}",
numbers.CumulativeSum().Last())
Dim somePath As String = "C:\Some directory\Some subdirectory\Somefile.txt"
System.Diagnostics.Debug.WriteLine("The path contains the following parts")
For Each partialPath As String In somePath.Split("\").CumulativePath()
System.Diagnostics.Debug.WriteLine(" - '{0}'", New Object() {partialPath})
Next
Dim somePath2 As String = "C:\Windows\Some non-existent directory\Some non-existent file.txt"
System.Diagnostics.Debug.WriteLine("The path parts are valid as follows")
For Each partialPath As String In somePath2.Split("\").AllButLast().CumulativePath()
System.Diagnostics.Debug.WriteLine(
" - '{0}' does exist: {1}",
partialPath,
System.IO.Directory.Exists(partialPath))
Next
End Sub
End ModuleAnd the result from output is
The cumulative sum contains the following results
- 1
- 4
- 9
- 16
- 27
The cumulative sum total is 27
The path contains the following parts
- 'C:'
- 'C:\Some directory'
- 'C:\Some directory\Some subdirectory'
- 'C:\Some directory\Some subdirectory\Somefile.txt'
The path parts are valid as follows
- 'C:' does exist: True
- 'C:\Windows' does exist: True
- 'C:\Windows\Some non-existent directory' does exist: False
So the same results are achieved. In my opinion extending the LINQ in VB with enumerable methods, it may be much easier and clearer to use C# for the extension methods. The implementation is much smaller and more easily maintainable and I think that the C# code is quite easily understandable even with almost no experience with C# programming.
History
-
July 28, 2012: Alternative created.
I've been a programmer since mid 80's using languages like assembler, C/C++, PL/I (mainframe environment), pascal, VB (I know, I know, no comments please) and C# and utilizing different techniques and tools.
However I'm specialized in databases and database modeling. Mostly I have used products like Oracle (from version 6), SQL Server (from version 4.2), DB2 and Solid Server (nowadays an IBM product).
For the past 10+ years my main concerns have been dealing with different business processes and how to create software to implement and improve them. At my spare time (what ever that actually means) I'm also teaching and consulting on different areas of database management, development and database oriented software design.