21

I was taught this expression and pattern way back in the day. Sure, the name comes from old pumps that needed to be filled with water before they could pump water, but who cares? We're talking about code here.

Some really good examples and an explanation of what the pattern accomplishes would be welcome. How is this pattern regarded today?

Priming can sometimes get a defective loop working but at the cost of DRY. So it may be a brief stop on the way to a better design. Is this considered an anti pattern? Are there alternatives?

candied_orange
  • 102,279
  • 24
  • 197
  • 315
  • 2
    You'll find term "priming the pump" [in a stackoverflow answer](http://stackoverflow.com/a/27697452/1493294) and [a book](http://faculty.orangecoastcollege.edu/sgilbert/book/07-5-SentinelLoops-B/index.html). The term "priming read", found [here](https://answers.yahoo.com/question/index?qid=20110927203211AAYT88O), seems much the same. – candied_orange Apr 19 '16 at 18:06

1 Answers1

29

This metaphor almost certainly refers to the practice of establishing the first conditional check in a while loop. If you don't do this, the loop won't work. It is a well-established pattern, and it hasn't changed since the while loop was invented. The requirement for setting the initial condition in a while loop is not a defect.

int i = 0; // prime the pump
while (i < 10)
{
    Console.Write("While statement ");
    Console.WriteLine(i);
    i++; // set condition again
}

The primer can be a read statement, or whatever properly sets the initial condition. Setting the initial condition using a read statement is called a "Priming Read."

string line;

using (StreamReader file = new StreamReader("c:\\test.txt"))
{
    line = file.ReadLine(); // Priming read.
    while(line != null)
    {
        Console.WriteLine (line);
        line = file.ReadLine(); // Subsequent reads.   
    }
}

In C#, the two Readline() calls can be combined into a single statement within the conditional:

while ((line = r.ReadLine()) != null)
{
    Console.WriteLine (line);
}
Deduplicator
  • 8,591
  • 5
  • 31
  • 50
Robert Harvey
  • 198,589
  • 55
  • 464
  • 673
  • 1
    Nice. There are times when you need to do A and B in order with a test T exactly between them. The usual `A T(B A)` priming pattern does this but duplicates A. Any general alternatives to this general pattern? – candied_orange Apr 19 '16 at 18:25
  • 2
    See the last bit of code in my answer. – Robert Harvey Apr 19 '16 at 18:25
  • That one's a classic. Would you ever suggest using a break? – candied_orange Apr 19 '16 at 18:27
  • I'm not opposed to early exits from a loop if doing so simplifies the code. Sometimes you can just `return`. – Robert Harvey Apr 19 '16 at 18:28
  • Would love to see an example. – candied_orange Apr 19 '16 at 18:32
  • 1
    An example would be looking for the first occurrence of a string in each line of a text file. You would still need the `while` loop, but once you found the string in the line you just read, you could either `break` or `return`. – Robert Harvey Apr 19 '16 at 18:37
  • Found a decent [example of code](http://stackoverflow.com/a/6850411/1493294) that allows A and B to be any number of lines, avoids duplicating A, and puts a test between A and B. – candied_orange Apr 29 '16 at 06:38
  • While it’s not a defect, setting the initial condition outside the scope of the loop when it’s not used outside does cause a scope leak. Which is likely why they gave us the convoluted for(;;) loop. – candied_orange Sep 09 '22 at 18:39