tsJensen

A quest for software excellence...

Extend IEnumerable<T> with ForEach<T> and Once<T> Methods

A few days ago, a fellow programmer asked me a common question. How do you print odd numbers between one integer value and another. It's a common question and the quickest solution that came to mind is the common for loop with a simple if and the mod operator.

Later I began toying with the question and in combination wanted to experiment with an alternative to the limited ForEach extension method on IList<T>. What you see below is the result of a little tinkering and tweaking along with some fluent goodness.

I considered naming my custom extesion method ForEach but decided to use something different to remind myself that it is not your grandfather's ForEach extension method. So I named it ForEvery and in the middle of playing with that, I ended up creating the Once extension method on IEnumerable<T>.

class Program
{
   static void Main(string[] args)
   {
      PrintOdds(1, 100);
      Console.ReadLine();
   }

   static void PrintOdds(int x, int y)
   {
      Console.WriteLine("Odds with traditional for and if");
      for (int i = x; i <= y; i++)
      {
         if (i % 2 != 0) Console.Write("{0}, ", i);
      }

      Console.WriteLine();
      Console.WriteLine();
      Console.WriteLine("Odds with ToList and ForEach with if");
      Enumerable.Range(x, y - x + 1)
         .ToList()
         .ForEach(i =>
         {
            if (i % 2 != 0) Console.Write("{0}, ", i);
         });

      Console.WriteLine();
      Console.WriteLine();
      Console.WriteLine("Odds with Where then ToList and ForEach");

      Enumerable.Range(x, y - x + 1).Where(n => n % 2 != 0)
         .ToList().ForEach(i =>
         {
            Console.Write("{0}, ", i);
         });

      Console.WriteLine();
      Console.WriteLine();
      Console.WriteLine("Odds with Where and custom ForEach");

      Enumerable.Range(x, y - x + 1)
         .Where(n => n % 2 != 0)
         .ForEach(i =>
         {
            Console.Write("{0}, ", i);
         });

      Console.WriteLine();
      Console.WriteLine();
      Console.WriteLine("Odds with custom ForEvery fluent");

      Enumerable.Range(x, y - x + 1)
         .ForEvery(n => n % 2 != 0, i => 
         { 
            Console.Write("{0}, ", i);
         })
         .Once(n => n.Count() > 99, i =>
         {
            Console.WriteLine();
            Console.WriteLine("Once fluent");
            Console.WriteLine();
            Console.WriteLine("Evens with ForEvery fluent from {0} to {1}", i.Min(), i.Max());
         })
         .ForEvery(n => n % 2 == 0, i =>
         {
            Console.Write("{0}, ", i);
         });
   }
}

public static class EnumerableExtensions
{
   public static void ForEach<T>(this IEnumerable<T> collection, Action<T> action)
   {
      foreach (var item in collection)
      {
         action(item);
      }
   }

   public static IEnumerable<T> Once<T>(this IEnumerable<T> collection, 
      Func<IEnumerable<T>, bool> predicate, Action<IEnumerable<T>> action)
   {
      if (predicate(collection)) action(collection);
      return collection;
   }

   public static IEnumerable<T> ForEvery<T>(this IEnumerable<T> collection, 
      Func<T, bool> predicate, Action<T> action)
   {
      foreach (var item in collection)
      {
         if (predicate(item)) action(item);
      }
      return collection;
   }
}

Drop the code into a console app and run it. If you like these little extensions, I'd love to hear from you.

The 4 Keys to Effective Management

Effective management is simply pushing the right buttons and pulling the right levers at the right time. This requires sufficient information, analytic thought, rational decision, and consequential action. Asking questions and thoughtful contemplation are not enough. If you cannot make decisions and act upon them, you are a researcher; you are not a manager.

  1. Sufficient Information
     
  2. Analytic Thought
     
  3. Rational Decision
     
  4. Consequential Action

Every healthy human being manages something. You wake up hungry (information) and you think about bacon (thought) and you decide to limit yourself to two pieces (rational decision) and you throw three pieces in the pan (consequential action) just in case one of them burns even though you know you’ll eat it anyway. Okay, we’re not all perfect managers. Actually, I’ve never met one, so I’m not sure there is such a thing. Excuse me while I take a break to finish that third piece of bacon…

How to Manage Software Development

What the world needs is yet another blog post on how to manage software development, so why not write it myself I ask. Unable to find a good reason to stop here, I’ll give it a shot. If you continue to read, you and you alone will be responsible for anything you might learn.

There are books, graduate courses, and no end to rambling blogs, so I’ll shoot for brevity and clarity here in Part 1.

  1. Know Your Team
    Computers do not yet write software all that well by themselves, so you’re stuck managing the people. Your process or you dictate what they will work on and, by virtue of time constraints imposed, how they will work on it; this is the essence of management.
     
  2. Be Decisive and Take Action
    Collaboration is a meaningless waste of time unless it is followed by real decision and actions that lead to positive results. If you cannot make decisions and act upon them, you are a researcher; you are not a manager.
     
  3. Be Honest and Fair
    If you say one thing to your team on one day and deny having said it the next day, your team will lose confidence in you and rebuilding that trust may not be possible, so choose your words and promises carefully. And if you make a mistake, admit it readily and apologize where appropriate. Your team will see this as a mark of a true leader.
     
  4. Demand Accountability
    When you assert a process rule, enforce it. Hold team members accountable. Start with gentle reminders and further training but do not allow repeat offenders to skate without consequence. If you do, your process is not a process and it will fail.
     
  5. Eliminate Needless Meetings
    Developers generally hate meetings with good reason. Most meetings lack an agenda, lead to no discernable action items, and there is rarely a copy of the minutes minutes and action items distributed to attendees. Most software development requires long, uninterrupted periods of time to effectively solve problems and complete complex tasks. Useless meetings in the middle of the day can ruin a developer’s entire day, throwing his productivity into a spiral, so group meetings into a single day where possible to eliminate or reduce the disruptive effects.
     
  6. Review Everyone’s Work
    You may not understand the code, but having a developer walk you through the code, discussing the decisions made and showing off just a little will go a long way toward educating you and inspiring your developer. Review and discuss documentation, designs and test plans with interest. Spend the time to learn from and guide your team.
     
  7. Get Yourself Out of the Meetings Cyclone
    Decline a leadership training or management committee meeting from time to time in order to do some real managing. Remember, the word “manage” has its root in manus (hand). If you don’t put your hands on it, you can’t possibly manage it.
     
  8. Create and Shepherd Processes
    Everyone knows how to manage and can do so if you give them a process that establishes guidelines for what information should be considered, what decision making process should result, and how those decisions will become actions within the constructs of the process you have created.

Well, that’s enough for part one. More on the same topic later.

How One Meeting Can Blow A Programmer’s Whole Day

This morning I read a post by Seth Godin, a favorite of mine, which presented and discussed an essay written by Paul Graham of Y-Combinator called Maker’s Schedule, Manager’s Schedule.

I regret that this cogent essay and essayist have escaped my notice until now. It reveals what every programmer knows and has experienced with regard to meetings, and I’ve never found a better treatment of the subject.

It confirms with clarity that programming is a creative art, an act of creation or making. Such work cannot be effective and productive with multiple disruptive meetings every day. And sometimes it only takes one meeting, even a short one, to blow your whole day.

Why?

The content and contention in a single meeting can serve to distract a programmer to the point of rendering him effectively useless for the remainder of the day. This is true not only for the programmer but for anyone whose primary function is to make things of complexity.

Consider preventing the daily standup from becoming a meeting in which the resolution of identified impediments is attempted. And never allow the standup to devolve into an ad hoc project status review and planning meeting with the question, “When will you have X feature done?” being asked.

Consider piling all such meetings to which makers must be in attendance into one single day of the week, perhaps Friday or Monday to ensure the largest contiguous uninterrupted period for making, preferably in the late afternoon, so that we get every ounce of making from our makers that the company’s hard won cash can buy.

It’s more than something to think about. It’s something a manager could manage if the manager simply chose to do so, and it’s something a maker would appreciate more than can be expressed in written word.