tags:

views:

231

answers:

10

meaning something like...

foreach(blah b in blahblahs)
{
    writeOnMoon(b.name);
}
default
{
    writeOnMoon("No Blahs!");
}

default or, otherwise, or something like that, if this does not exist... do you think it should?

+3  A: 

Couldn't you just check blahblahs.length first?

lod3n
yeah but I was just checking because something like this would/could be handy and cleaner looking
shogun
@lod3n: Not always, because enumerations do not always have lengths.
Brian
foreach only requires IEnumerable so not always an option
Jeremy Wilde
You can always use the LINQ Enumerable.Length(), but this can also be very slow with a large enumerable.
Reed Copsey
@Reed I think you mean `Count()`
Quintin Robinson
@Reed: Isn't "Any" (your own suggestion!) a much better choice than "Length" ?
Brian
@Brian- Any is the better choice.
RichardOD
+10  A: 

how about:

    bool run = false;
    foreach (var item in collection)
    {
        run = true;
        // Do stuff
    }
    if (!run)
    {
        // Other Stuff
    }
JDunkerley
That's pretty nice.
lod3n
will a bool always be false right after birth?
shogun
You will receive an uninitialized variable error. His code should read: `bool run = false;`
sixlettervariables
yes - default value for a bool is false
JDunkerley
It's a better practice to explicitly initialize it.
clintp
1+ cause its simple
Richard
Indeed better to initialise, have updated to reflect this. (Didnt have visual studio in front of me so forgot!)
JDunkerley
Well at least ReSharper complains about redundant initialization if you do bool run = false; so yes, it would seem so ^^
Oskar Duveborn
@Oskar: yes that feature of Resharper is annoying, Visual Studio wants one, Reshaper the other
JDunkerley
+1  A: 

No, there is not.

Frank Schwieterman
+1  A: 

Nope, there's no specific syntax in C# that will do what you want.

You're forced to devise your own approach (like what JDunkerley's example shows).

Joseph
+4  A: 

There isn't a keyword to do this.

You can do:

if (blahblahs.Any())
{
    foreach(blah b in blahblahs)
    {
        writeOnMoon(b.name);
    }
}
else
{
    writeOnMoon("No Blahs!");
}
Reed Copsey
That does have the disadvantage of calling `GetEnumerator()` twice. Not *usually* a problem, but occasionally it might be.
Jon Skeet
It's cleaner and easier to read than the other proposed solutions though.
Meta-Knight
+3  A: 

This doesn't exist.

I don't think this should be in the language because it really doesn't allow you to do anything new, nor does it make any current complex tasks much simpler.

Michael
Some language features/commands exist only to make certain "patterns" more maintainable (ex. easier to understand when first looking at the code). In theory, this would be one of those. There's also the point that it makes it "safer" as in "less likely to code wrong"... the primary reason (in my mind) for using the new Java for syntax over the older (index based) syntax.
RHSeeger
+3  A: 

No, but you could write an extension method so you could write:

collection.ForEachOrDefault(b =>
{
    WriteOnMoon(b.name);
}, () =>
{
    WriteOnMoon("No Blahs!");
});

Admittedly I don't think I'd recommend it... but here's the code:

public static void ForEachOrDefault<T>(this IEnumerable<T> source,
    Action<T> forEachAction, Action defaultAction)
{
    // Nullity checking omitted for brevity
    bool gotAny = false;
    foreach (T t in source)
    {
        gotAny = true;
        forEachAction(t);
    }
    if (!gotAny)
    {
        defaultAction();
    }
}
Jon Skeet
A: 
IEnumerable myCollection = GetCollection();
if(myCollection.Any())
{
    foreach(var item in myCollection)
    {    
        //Do something
    }
}
else
{
   // Do something else
}
Micah
`Any()` is better than `Count() != 0` as it can stop as soon as it's found the first element. I think you meant that to be != 0 btw.
Jon Skeet
Thanks Jon. I didn't know about the Any() method. Thanks!
Micah
A: 

No. But you can try to invent a simple extension method - for simple cases it will do...

public static class EnumerableExtension
{
   public static void IfEmpty<T>(this IEnumerable<T> list, Action<IEnumerable<T>> action)
   {
       if (list.Count() == 0)
         action(list);
   }
}

foreach (var v in blabla)
{
}
blabla.IfEmpty(x => log("List is empty"));

Maybe you'll even be able to create re-usable actions then. Though it doesn't really make much sense.

queen3
Keep in mind IEnumerable<T>.Count() may be quite a bit more expensive than O(1).
sixlettervariables
You'd just need to replace list.Count() == 0 with "!list.Any()" and it becomes O(1)
Meta-Knight
+1  A: 

Python has this (for ... else ...) and I really miss it in C#.

With LINQ you can do something like this:

public static IEnumerable<T> IfEmpty<T>(this IEnumerable<T> source, Action action)
{
    var enumerator = source.GetEnumerator();
    if (enumerator.MoveNext())
        do yield return enumerator.Current; while (enumerator.MoveNext());
    else
        action();
}

mylistofobjects.Each(...).IfEmpty(() => { /* empty list */ });
Per Erik Stendahl