开发者

Change Default Value of a Class

public class MyClass
{
    public string myString;

    public MyClass(string s)
    {
        this.myString = s;
    }
}

In IEnumerable<MyClass> how can I change the d开发者_运维百科efault value of FirstOrDefault() method

For example I want to return new MyClass("HelloWorld");

Edit: Is there a way to override default value of a Class?

Like Default Value of MyClass is new MyClass("Default");


You can't directly change it. But you have a few alternatives.

If your sequence contains no nulls you can use:

MyClass result = seq.FirstOrDefault() ?? new MyClass("HelloWorld");

Or you can implement your own version which takes a parameter for the default value:

    public static T FirstOrDefault<T>(this IEnumerable<T> source, T defaultValue)
    {
        using (IEnumerator<T> enumerator = source.GetEnumerator())
        {
            if (enumerator.MoveNext())
                return enumerator.Current;
            else
                return defaultValue;
        }
    }

    public static T FirstOrDefault<T>(this IEnumerable<T> source, Func<T, bool> predicate, T defaultValue)
    {
        using (IEnumerator<T> enumerator = source.Where(predicate).GetEnumerator())
        {
            if (enumerator.MoveNext())
                return enumerator.Current;
            else
                return defaultValue;
        }
    }

You could also use a different name for your this implementation of FirstOrDefault, but since it doesn't collide with any of the existing overloads, I just used the same name.

https://github.com/CodesInChaos/ChaosUtil/blob/master/Chaos.Util/LinqExtensions.cs


As an equivalent alternative to CodeAsChaos's good answer, you could also do the somewhat shorter:

public static T MyFirstOrDefault<T>(
    this IEnumerable<T> sequence, 
    T myDefault)
{
    foreach(T item in sequence)
        return item;
    return myDefault;
}

public static T MyFirstOrDefault<T>(
    this IEnumerable<T> sequence, 
    Func<T, bool> predicate, 
    T myDefault)
{
    return sequence.Where(predicate).MyFirstOrDefault(myDefault);
}


You could define an extension method like this:

public static T FirstOrDefault<T>(this IEnumerable<T> source, T defaultValue)
{
    foreach (T x in source)
    {
        return x;
    }
    return defaultValue;
}


Why don't just use DefaultIfEmtpy()?

For instance:

var result = this.MyClasses
    .Where(c => c.SomeCondition)
    .Select(c => c)
    .DefaultIfEmpty(new DefaultClass())
    .First();


I'm going to instead of using generics, just tie it to an enumerable of your class:

public static MyClass FirstOrDefault(this IEnumerable<MyClass> source)
{
    foreach (var x in source)
    {
        return x;
    }
    return new MyClass("hello world"); 
    //OR, could be made a bit nicer by making a static method in your class
    return MyClass.Default();
}

This will do what you want, but only for your class. If this is acceptable, then this is by far the easiest and shortest way of doing it.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜