The "apply" function in jvascript and in Scala
Part 1 - javascript:
This code snipet demonstrates a kind of inheritance (it's more like sharing/mixing) in javascript
1> Where "const coffee" acts similar to a Java Abstract Class. Although there is a small different here, in which, Java would not allow to have "size" and "sugarOrMilk" because these 2 variables are not defined within inner scope of "coffee"
const coffee = {
cup: function() {
return this.size + "-" + this.sugarOrMilk;
}
}
const order = {
size: "Small",
sugarOrMilk: "Sugar"
}
// Output of below statement would be: "Small - Sugar":
coffee.cup.apply(order);
2> "order" acts like a Java Entity (in this case, it's more like an instance than an object), and with statement "coffee.cup.apply(order)", in enables the realization of attributes "size" & "sugarOrMilk" within execution scope of coffee
Further reading, in order to understand more about "apply" and mechanism of how "const coffee" accept the value of "size" and "sugarOrMilk", you need to read more about the concept of "Dynamic Scope" & "Lexical Scope", as well as mixin mechanism of Javascript.
It literally demands "coffee" to execute function "cup" with "apply"-ing the the values of "size" and "sugarOrMilk" from the inner-scope of instance "order"
P/S: I use the term "inheritance" here to refer to a slightly similarity of the usage rather than the exact meaning of the terminology
Part 2 - Scala:
Related to Functional Programming perspective, particularly to Scala, it also provides the function "apply".
I don't know about the "behind the scene" idea or the implementation mechanism of the function "apply" of Scala, but, regarding the usage, i.e "how-to-use"; "apply" function in Scala works differently.
For example, if we define Scala object as below
Please note that, in Scala, function is also an object
object Coffee {
val cup = new Function2[String, String, String] {
def apply(size: String, sugarOrMilk: String): String = size + "-" + sugarOrMilk
}
def main(args: Array[String]): Unit = println(cup("small", "sugar"))
}
We can have 2 ways to trigger function "cup"
Recommended by LinkedIn
1. Explicitly: cup.apply.("small", "sugar")
2. Implicitly: cup("small", "sugar")
This is different with javascript, the logic of it is not dealing with Scope, but dealing with defining a "default" method for an object, and in this case, that object is of type Function2.
And, if we construct the same example in a new way as below by using a technique called "partially applied function":
class Drink(x: String) {
def apply(y: String) = x + "-"+ y
}
object Coffee {
val makeDrink = new Drink("coffee")
// val result = makeDrink.apply("sugar") <-- Explicitly trigger "apply"
val result = makeDrink("sugar") // <-- Implicitly trigger "apply"
def main(args: Array[String]): Unit = println(result)
}
We can see that, if we only look at makeDrink("sugar"), we may think that, string "coffee" has been implicitly initialized somewhere, but, actually, string "coffee" has been initialized at the moment we instantiate the object "makeDrink".
So, even though the concept of "apply" function in Javascript and Scala seems to be similar
i.e: apply is a function that applies a function to arguments
refer to: https://en.wikipedia.org/wiki/Apply
The way that it is used in javascript & Scala are different.
Other than that, the difficult part of learning Scala language on the whole is that the beginning section for beginners is not quite clear. There is not a clear cut of the right simple way to do simple things. Because, even a very simple program could be done in multiple ways with various complex ideas behind, even for a very simple solution.
P/S: