I want to execute a function on all the objects within a List of objects using LINQ. I know i saw something similar on SO before but after several failed search attempts, i am posting this question
+8
A:
Try the following if it is actually of type List<T>
.
C#
var list = GetSomeList();
list.ForEach( x => SomeMethod(x) );
' Alternatively
list.ForEach(SomeMethod);
VB.Net
Dim list = GetSomeList();
list.ForEach( Function(x) SomeMethod(x) );
Unfortunately .ForEach is only defined on List<T>
so it cannot be used on any general IEnumerable<T>
type. Although it's easy to code such a function
C#
public static void ForEach<T>(this IEnumerable<T> source, Action<T> del) {
foreach ( var cur in source ) {
del(cur);
}
}
VB.Net
<Extension()> _
Public Shared Sub ForEach(Of T)(source As IEnumerable(Of T), ByVal del As Action(Of T)
For Each cur in source
del(cur)
Next
End Sub
With this you can run .ForEach on any IEnumerable<T>
which makes it usable from practically any LINQ query.
var query = from it in whatever where it.SomeProperty > 42;
query.ForEach(x => Log(x));
EDIT
Note to use the .ForEach for VB.Net. You must chose a function that returns a value. It's a limitation of lambda expressions in VB.Net 9 (VS 2009). But there is o work around. Say you want to call SomeMethod which is a Sub. Simply create a wrapper which returns an empty value
Sub SomeMethod(x As String)
...
End Sub
Function SomeMethodWrapper(x As String)
SomeMethod(x)
Return Nothing
End Function
list.ForEach(Function(x) SomeMethod(x)) ' Won't compile
list.ForEach(function(x) SomeMethodWrapper(x)) ' Works
JaredPar
2009-05-08 19:19:17
i would like to take the first approach you have mentioned. does that works similarly in vb.net
Vikram
2009-05-08 19:21:01
@Vikram, yes you can. I updated the code to include VB.Net samples.
JaredPar
2009-05-08 19:24:12
System.Linq already provides an extension for IEnumerable<T> that gives you a .ToList() which you can use, right?
Terry Donaghe
2009-05-08 19:25:27
@Terry yes you can take that approach and it will work. But it does force everything into a single in memory collection. Nothing inherently wrong with that but generally people avoid it when using LINQ.
JaredPar
2009-05-08 19:29:52
thanks for the adding the snippet, however when i try to use the syntax you have given for vb.net, it does not works. it does not even lets me compile.
Vikram
2009-05-08 19:32:55
this is what i tried. and when i try to write SomeMethod(x), it shows me blue underlining saying that "Expression does not produce value". Dim list = GetSomeList()list.ForEach( Function(x) SomeMethod(x) )
Vikram
2009-05-08 19:35:27
@Vikram, that's because ForEach is a Sub and returns no value. If you want to modify the items in the list and return a new one, use Select instead of ForEach
JaredPar
2009-05-08 19:38:11
i dont want to return any value but simply load some child elements in the object
Vikram
2009-05-08 19:40:28
@Vkiram, I see the issue now, will update answer in a sec
JaredPar
2009-05-08 19:48:54