Take the 2-minute tour ×
Programmers Stack Exchange is a question and answer site for professional programmers interested in conceptual questions about software development. It's 100% free, no registration required.

When I write programs I using pass by value or pass by reference always seem to be logical methods. When learning about different programming languages I came across pass by name.

Pass by name is a parameter passing method that waits to evaluate the parameter value until it is used. See Stack Overflow pass by name question for more information on the method.

What I would like to know is: what are some good examples and/or reasons to use pass by name and should it be re-introduced into some more modern languages.

share|improve this question

closed as primarily opinion-based by gnat, MichaelT, Robert Harvey, World Engineer Dec 3 '13 at 5:40

Many good questions generate some degree of opinion based on expert experience, but answers to this question will tend to be almost entirely based on opinions, rather than facts, references, or specific expertise.If this question can be reworded to fit the rules in the help center, please edit the question.

    
Looks like call-by-name in the term-substitution sense can be implemented as a combination of lazy evaluation (available in Haskell, Scala, various Lisps) and dynamic scoping (available in Haskell, various other Lisps). –  Jon Purdy Dec 1 '13 at 20:43
1  
@JonPurdy Haskell is call by name, it just also shares the result. This invalidates the term-substitution way of thinking though. You can force reevaluation simply by wrapping the argument in a trivial lambda \_ -> a when called will eval a each time. –  jozefg Dec 2 '13 at 4:16

4 Answers 4

up vote 2 down vote accepted

Some of the advantages are described in a description of pass by name linked to in your linked question's answer.

The advantages of pass-by-name are (paraphrased from the article):

  1. It has a simple semantic model as textual substitution.
  2. Modification and re-evaluation of argument expressions has useful applications, such as Jensen's device. (Ed: Described in the second section)
  3. Argument expressions are not necessarily evaluated. Here, y is not evaluated if x is false:

    boolean procedure and (x, y);
      boolean x, y;
    begin
        if x then return y else return false
    end;
    

Would I use it?

I see no reason to, even considering the advantages put forward. Pointers and short-circuit evaluation prevent expression evaluation as much as I need it, and I'm quite happy with the semantic models I use regularly.

share|improve this answer
3  
eval() is just about as insecure as you can get. Unless you have a language in mind that can sandbox the eval'd statement (which would then mean it's nowhere near as flexible), which you really need to indicate. –  Izkata Sep 6 '12 at 18:06

Scala is an example of modern language that supports call-by-name evaluation (as well as call-by-value, which is the default). As you said, the parameter is lazily evaluated.

This feature can be used for creating your own control structure. The code given by Axidos in his answer is a simple, but good example.

There are other examples in the book Programming in Scala. I'll try to post these examples here tonight.

share|improve this answer

Here's what I think is a super simple example of passing something by name:

// JavaScript
function apply(a, b, f) { return f(a,b); }

function add(a,b) { return a + b; }

var result = apply(2, 4, add); // result is now 6

// The same in C using function-pointers
int apply(int a, int b, int (*f)(int,int)) { return f(a,b); }

int add(int a, int b) { return a + b; }

int result = apply(2, 4, add); // result is once again 6

Notice how I'm passing the name of the function add in as a parameter in the apply function, just like I would with any other variable. The f function isn't evaluated at the time of declaration, simply because it can't be evaluated; its body doesn't exist at declaration. But this opens up for so many possibilities in terms of reducing boilerplate code. Like say you have 2 functions/methods that both do the exact same thing, apart from just one very specific line; instead of having to write the exact same thing twice, you can write it once, and then pass the one line of code that stands out, by name.

Let me show you a more elaborate example from one of my projects:

// C# snippet from a web-communication utility
private static void PostHelper(string inputUri, Action<WebClient, Uri> clientFunction) {
    var client = new WebClient();
    client.Headers[HttpRequestHeader.ContentType] = "application/json";
    var uri = new Uri(inputUri);
    clientFunction(client, uri);
}

public static void Post(string inputUri, string jsonInput) {
    PostHelper(inputUri, (client, uri) => client.UploadString(uri, "POST", jsonInput));
}

public static void PostAsync(string inputUri, string jsonInput) {
    PostHelper(inputUri, (client, uri) => client.UploadStringAsync(uri, "POST", jsonInput));
}

If I hadn't used C#'s ability to pass by name, in the form of higher order functions, I would've had to write the code in the PostHelper twice, with the one minor change that one says UploadString, and the other says UploadStringAsync, doing like I did saves me repeated code, and it even lets me expand it later if I want to add more variations of the method. Because clientFunction is evaluated lazily I can make my code much more scalable.

share|improve this answer

Pass by name has some purpose.

Indeed we are saying that pass by name uses textual substitution or otherwise macro substitution.

If we are using pass by value or pass by reference we are merely passing values or addresses, but we can't pass an expression such as i*x[i]; (in pass by reference it evaluated into a temporary location whose address is passed ), but it is possible with pass by name.

For example if we want to perform the sum of the expression i*x[i] where i varies from 1 to 5 using a function, we can write a function that uses pass by reference as written below (don't mind the syntax)

  *procedure sum (int low, int high, int i , real exp)
  { 
       begin

         real S;
         S := 0;
         for i := low step 1 until high do
           {  S := S + Exp;
             Sum := S}
       end;*
 }

then a call such as sum(1,5,i,x[i]) will find out the sum of series i*x[i], where Exp gets literally substituted for i*x[i].

share|improve this answer

Not the answer you're looking for? Browse other questions tagged or ask your own question.