Archive | LINQ RSS feed for this section

C# Actions part 2: Lazy evaluation

14 Jul

Lazy Evaluation example:

In a previous post I talked about C# Actions and how they are a useful feature that could provide new shorthand for lazy evaluation. I have since found an excellent article [1] which demonstrates lazy evaluation with LINQ. The advantages in that article show how LINQ queries can minimize memory usage by evaluating upon enumeration rather than just allocating memory for everything the query would return.

Func

Actions are delegates that have a void return type. This makes sense if you are using Actions as event handlers, but for other use cases you will want a return type. In these cases you will want to use Func. One issue I have seen with Func is when you want don’t know how many parameters your function is going to take. If the number is variable then you must implement up to the amount of parameters you want (if overloading). I noticed a few examples of that in the Ninject 1.x source code. To generalize Func and Actions you can use the ‘Delegate’ type (note: the captialization).

A real world use case

A reason for lazy evaluation could be that you want to perform a group of service calls at one time. The service calls could be a transaction style interaction which would want to be disposed afterwards and some of the service calls could be surplus to requirement. If I had a user interface which required a list of products to be loaded, then that screen may not need that data reloaded if it is moving from a screen which has that data loaded. That service call could be pre-evaluated (ie lazy evaluation) to check to see if it is necessary.

Updating an item in a list without a reference with lambdas

15 Feb

I have to confess I am enjoying lambdas a bit much. I am making this post to show a cool way of avoiding code loops (there are still loops in CLR of course).

private void UpdatePerson(Person updatedPersonObject)
{
    var outOfDatePerson = _people
            .First(person => person.Id == updatedPersonObject.Id);
    int index = _people.IndexOf(outOfDatePersonObject);
    _people[index] = updatedPersonObject;
}

private void UpdatePerson_OldCSharp(Person updatedPersonObject)
{
    int outOfDatePersonIndex = 0;
    for (int i = 0; i < _people.Count ; i++ )
    {
        if (_people[i].Id == updatedPersonObject.Id)
        {
            outOfDatePersonIndex = i;
            break;
        }
    }
    _people[outOfDatePersonIndex] = updatedPersonObject;
}

From the two code samples it is worth noticing the difference in the number of lines and in the hierarchical nature of the code. The traditional C# for loop approach (the second method) leads me to cringe from a maintenance point of view. Each line of code is highly contextual and relies heavily on multiple levels of language constructs.

The first method (the lambda way) to me is much more readable and also maintainable. There is a flat hierarchy which is much easier to read as it doesn’t involve following the loop through code. I argue it is easier to maintain as the lines can change order more and will still be doing the same thing. It is also easier to update as there is less code.

Implicit parameter specification with Lambdas

13 Feb

On the last line of code in the following code listing you will notice that the method of IList<T>.Add(T item) is called but with no parameter.

//our resulting output
IList<Person> lecturersEnrolledForStudy = new List<Person>();

//students and lecturers can enrol for study.
var newStudentEnrolementList = new List<Person>();

//filter the students out
var lecturersEnrollingInAClass = newStudentEnrolementList
                                    .Where(person => person.isLecturer)
                                    .ToList();

//add lecturers that are enrolling to the enrolled list.
lecturersEnrollingInAClass.ForEach(lecturersEnrolledForStudy.Add);

The parameter is still being populated like as if the following code was written:

lecturersEnrollingInAClass
            .ForEach(item => lecturersEnrolledForStudy.Add(item));

The parameter is inferred by the compiler just as the type of the “item” variable is by the lambda expression/list type. For those of us who are being weaned off traditional loops for these sorts of list interactions might find that it is more natural to think of the list that we are adding too first, and the list that the information is coming from second. This has reversed with lambdas.

A point worth making is that while this example I have provided is simple and could be done using an AddRange method, it is not as extensible and hence I suggest not using it. An example of the .ForEach extention methods extensibility would be that it can ‘addrange’s across different types and at different depths of objects. An example of this could be:

lecturersEnrollingInAClass
            .ForEach(item => lecturesNamesList.Add(item.Name));

In conclusion this is a handy shorthand to use with lambdas. If you already use the Resharper plug-in, this shorthand will have been suggested to you.

LINQ for show, Lambda for pro

13 Feb

When first utilizing the new query techniques of .NET 3.5 such as LINQ and Lambda expressions I would always choose LINQ over lambda expressions. This was for two reasons:

1. LINQ looked more natural

2. Lambda expressions or the LINQ extension methods to be more accurate are often hidden away because either you are not using the correct type to access them, or don’t have the System.LINQ library in the using section.

As time has progressed I have realised that I now use lambda expressions almost exclusively. I feel that looking deeper into LINQ has facilitated this, specifically understanding the typing behind LINQ. Ultimately it comes down to preference as the compiler changes LINQ to use extension methods, see: here

An example of the difference in sytnax is:

var d = (from mp in MyProducts

where mp.Price < 50d

select mp);

var f = MyProducts.Where(mp => mp.Price < 50d)

I think that when your queries are smaller, that lambda expressions are quicker to write and more natural to the rest of C#. When a query becomes very large LINQ could be more concise but I haven’t yet come across such a situation. Also I am not a fan of single huge queries as it is an inconvenience for other developers if they need to modify a query. Its bigger, so takes longer to read, and multiple smaller queries means that code be executed in between queries. With PLINQ however there could be an advantage in have a single larger query, however I am not taking PLINQ into consideration today.

Linq Anonymous return types

21 Jan

I have decided to make a post about LINQ anonymous types with respect to typing after talking to some colleagues. Below I compare 2 LINQ statements, the first being with an anonymous type being returned, the second with a specified type being returned.

Anonymous type:

IList<Window> windows = new List<Window>();

var query = from window in windows

where window.Visibility == Visibility.Hidden

select new

{

Visibility = window.Visibility,

Title = window.Name

};

image

Specified Type:

IList<Window> windows = new List<Window>();

var query = from window in windows

where window.Visibility == Visibility.Hidden

select new myType

{

Visibility = window.Visibility,

Title = window.Name

};

image

Comparing the two return types shown in both of the images, we can see that both return the same data. The thing we cannot see is that an anonymous type is scoped to the method that the LINQ statement is in. This means that we can’t pass query off to another method unless we extract the data we want to a non anonymous type.