Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
214 views
in Technique[技术] by (71.8m points)

Two ways of defining functions in Scala. What is the difference?

Here is a little Scala session that defines and tries out some functions:

scala> def test1(str: String) = str + str;    
test1: (str: String)java.lang.String

scala> test1("ab")
res0: java.lang.String = abab

works nicely.

scala> val test2 = test1
<console>:6: error: missing arguments for method test1 in object $iw;
follow this method with `_' if you want to treat it as a partially applied function
       val test2 = test1
                   ^

oops.

scala> val test2 = test1 _
test2: (String) => java.lang.String = <function1>

scala> test2("ab")
res1: java.lang.String = abab

works well!

Now, I've seen the _ syntax when folding (_ + _, etc). So as I understand it _ basically means "an argument". So test1 _ basically means a function with an argument, which is given to test1". But why isn't that exactly the same as just test1? Why is there a difference if I append a _?

So I kept exploring...

scala> val test3 = (str: String) => str + str
test3: (String) => java.lang.String = <function1>

scala> test3("ab")
res2: java.lang.String = abab

scala> val test4 = test3
test4: (String) => java.lang.String = <function1>

Here it works without _! What's the difference between a defed function, and a valed function?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

The def declares a method within a surrounding object/class/trait, similar to the way you define methods in Java. You can only use defs within other objects/classes/traits. In the REPL, you cannot see the surrounding object because it's "hidden", but it does exist.

You cannot assign a def to a value, because the def is not a value - it's a method in the object.

The (x: T) => x * x declares and instantiates a function object, which exists at runtime. Function objects are instances of anonymous classes which extend FunctionN traits. FunctionN traits come with an apply method. The name apply is special, because it can be omitted. Expression f(x) is desugared into f.apply(x).

The bottomline is - since function objects are runtime values which exist on the heap, you can assign them to values, variables and parameters, or return them from methods as return values.

To solve the issue of assigning methods to values (which can be useful), Scala allows you to use the placeholder character to create a function object from a method. Expression test1 _ in your example above actually creates a wrapper function around the method test1 - it is equivalent to x => test1(x).


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...