[SOUND].

Now that we've learned anonymous functions, I want to show you one

programming pattern that's actually poor style.

It's actually an over use of anonymous functions where you don't need them,

and that's something that I like to call unnecessary function wrapping.

Although, I'm pretty sure I made up that particular term for it, but not the idea.

So, let's go over here, use our same higher order function we've

been playing around with for a long time, n times, and try to write one of the

things it's really useful for, which is taking the Nth tail of some list.

So I'm going to have N and Xs, which is going to be my list, and I want to N

times take the tail of the list, so my second and third argument to N times are

clearly going to be N and Xs. But for the first argument, we realize,

well, we just need a function right here that takes the tail of its argument, and

we just learned anonymous functions, so let's use them.

Right? Let's say, fun Y, tail of Y.

And this will work and it's correct and we feel good about using anonymous

functions, and I'm going to argue this as actually just a very minor bit right

there of, of inferior style. And here's why.

Let's look at this function we wrote and let's describe what it does.

This is a function that takes one argument and returns the list tail of

that argument. Is there a simpler expression, a more

straightforward way of writing down here an expression that is a function that

takes the tail of its argument? Yes, there is, and that is to just write

tail. Right?

Tail is a variable that, when we look it up in the environment, we get a function

that does exactly the right thing. The other version is wrapping that

perfectly good function that does exactly what we want with another function that's

going to do the same thing. It's just longer.

It's a tiny bit slower, since one function has to call another one, and it

obscures the fact that what we want to pass to N times is a perfectly good

function for taking the tail. So that's unnecessary function wrapping.

To kind of explain in general what's going on, let me try an analogy for you.

'Kay. We've emphasized previously, and you may

have seen in previous programming courses, that you shouldn't write things

like if X then true, else false. This is an expression that returns true

if X is true and false if X is false, but another thing that does that is just X.

Right? We don't need the if then else X is

already the expression that we want. And similarly, if you have a function like

take NX and return the result of calling F with X,

the expression, F, will do just as well. So that's the most common situation,

where you'll see this unnecessary function wrapping is when we have an

anonymous function that has this form, that all it does is pass its argument to

another function, then we should just use that function, like tail in our example,

in place of it. That's really the idea.

Let me show you one other related thing. somewhat similar, also unnecessary

function wrapping, but comes up a little less often and is a little less obvious,

that's what's going on. let me, for example, you probably don't

know this, in the standard library for ML, ML, there's a function list.rev that

reverses a list. So suppose you were going to use this a

lot, or you had trouble remembering, that it was list dot, and in some file, you

just wanted, your own function, rev, that did the same thing, but, of course, you

don't want to re-implement reverse, there's a perfectly good library

function. So you would write it like this.

So this is also unnecessary function wrapping.

I have a function reverse that takes in one argument, x's, and returns, it's body

is calling list.rev rev with x's. If we use the sort of de-sugared version

of this, that might be more obvious, since our function, rev, is not

recursive. We could have written it like this.

And now we see indeed this anonymous function here has exactly the pattern

that is this unnecessary function wrapping,

and indeed, a, a superior style solution would be to just write val rev equals

list.rev. Right.

This may look a little strange to you, but it's a great use of first class

functions. I'm defining a variable rev, and what I

will bind it to is the result of evaluating this expression list.rev.

So I look up list.rev in my environment, I get a function back, and so rev will

now be bound to the same function as list.rev.

So whenever you want a shorter or simpler, easy to remember name for a

function that's defined somewhere else, I really prefer this third version to the

first version because again it's a little simpler, it's more direct to what it is

you're doing and it's actually even a little bit faster because you're not

making an unnecessary function call.