У математиков есть свои маленькие забавные способы, поэтому вместо того, чтобы говорить «тогда мы вызываем функцию, f
передавая ее x
в качестве параметра», как сказали бы мы, программисты, они говорят о «применении функции f
к ее аргументу x
».
В математике и информатике Apply - это функция, которая применяет функции к аргументам.
Википедия
apply
служит для устранения разрыва между объектно-ориентированной и функциональной парадигмами в Scala. Каждая функция в Scala может быть представлена как объект. Каждая функция также имеет тип OO: например, функция, которая принимает Int
параметр и возвращает Int
тип, будет иметь тип OO Function1[Int,Int]
.
// define a function in scala
(x:Int) => x + 1
// assign an object representing the function to a variable
val f = (x:Int) => x + 1
Поскольку в Scala все является объектом, f
теперь его можно рассматривать как ссылку на Function1[Int,Int]
объект. Например, мы можем вызвать toString
метод, унаследованный от Any
, что было бы невозможно для чистой функции, потому что у функций нет методов:
f.toString
Или мы можем определить другой Function1[Int,Int]
объект, вызвав compose
метод f
и связав две разные функции вместе:
val f2 = f.compose((x:Int) => x - 1)
Теперь, если мы хотим фактически выполнить функцию или, как математик говорит «применить функцию к ее аргументам», мы бы вызвали apply
метод Function1[Int,Int]
объекта:
f2.apply(2)
Запись f.apply(args)
каждый раз, когда вы хотите выполнить функцию, представленную в виде объекта, является объектно-ориентированным способом, но добавит много беспорядка в код, не добавляя много дополнительной информации, и было бы неплохо иметь возможность использовать более стандартную запись, такую как как f(args)
. Вот где Scala-компилятор входит, и когда у нас есть ссылка f
на объект функции и пишется, f (args)
чтобы применить аргументы к представленной функции, компилятор молча расширяет f (args)
вызов метода объекта f.apply (args)
.
Каждая функция в Scala может рассматриваться как объект, и она работает по-другому - каждый объект может рассматриваться как функция, если у него есть apply
метод. Такие объекты можно использовать в обозначениях функций:
// we will be able to use this object as a function, as well as an object
object Foo {
var y = 5
def apply (x: Int) = x + y
}
Foo (1) // using Foo object in function notation
Есть много случаев использования, когда мы хотим рассматривать объект как функцию. Наиболее распространенным сценарием является фабричный шаблон . Вместо добавления беспорядка в код, используя фабричный метод, мы можем apply
возражать против набора аргументов, чтобы создать новый экземпляр связанного класса:
List(1,2,3) // same as List.apply(1,2,3) but less clutter, functional notation
// the way the factory method invocation would have looked
// in other languages with OO notation - needless clutter
List.instanceOf(1,2,3)
Так что apply
метод - это просто удобный способ сократить разрыв между функциями и объектами в Scala.