Что такое _: в Свифт сказал мне?
Что означает одиночное подчеркивание в определениях функций?
например. map(_:)
Я понимаю, что при определении функций я могу сделать:
func myFunc(_ string: String) { ... }
Я бы тогда ссылался на это как myFunc(_:)
вместо myFunc(_string:)
, т.е. целенаправленно скрывая имя параметра?
Ответы
Ответ 1
Swift требует соглашения о том, что означает имя функции, включая не только имя функции (перед круглыми скобками), но и внешние имена параметров. Соглашение заключается в том, что за именами следуют двоеточия. Итак, здесь объявление функции (в Swift 2.0):
func myFunc(param1 param1:String, param2:String, param3:String) {}
И вот это имя функции:
myFunc(param1:param2:param3:)
В реальной жизни, однако, возможно (действительно, вероятно), что один или несколько параметров не будут вытеснять любое имя. Таким образом, нам нужно заполнить это имя. Подчеркиванием является то, что заполнитель - так же, как подчеркивание является символом в декларации, подавляющим экстернализацию имени. Итак, вот еще одно объявление функции (в Swift 2.0):
func myFunc2(param1:String, _ param2:String, _ param3:String) {}
И вот это имя функции:
myFunc2(_:_:_:)
[Здесь важна спецификация Swift 2.0. В Swift 2.0 первое имя параметра всегда не экстернализируется по умолчанию, а остальные имена параметров по умолчанию вытесняются. В Swift 1.2 и ранее правила экстернализации зависели от того, где появилось объявление, которое было излишне противоречивым и запутанным.]
Ответ 2
_
используется для определения того, что параметр не назван
Если у вас есть несколько _
, это означает, что вам не нужно указывать параметры в вызове функции
func myFunc(name:String, _ age:String){
}
myFunc("Milo", "I'm a really old wizard")
Если вы не используете символ подчеркивания, вы должны использовать
myFunc("Milo", age: "I'm a really old wizard")
В вызовах функций _
не требуется. Он просто используется, чтобы указать, что что-то не имеет имени.
Что касается того, как вы будете ссылаться на свою функцию, вам не нужно будет передавать какое-либо имя для вызова функции.
Но так как вы также не определяете тип параметра, это кажется мне неправильным примером (он по крайней мере не работает в xCode 7 с быстрым 2.0)
Edit:
Так как swift 3.0
myFunc(name: "Milo", age: "I'm a really old wizard")
Следует использовать
Ответ 3
При обращении к функции, чтобы устранить неоднозначность, необходимо указать имя функции вместе с внешними именами любых ожидаемых параметров.
Например,
func myFunc(myString string: String) { ... }
и
func myFunc(_ string: String) { ... }
представляют две различные функции: ту, где для первого параметра String предоставляется внешняя метка при вызове функции, а другая - без метки, например:
myFunc(myString: "hi")
и
myFunc("hi")
Итак, чтобы идентифицировать функцию, мы включаем внешнюю метку для каждого параметра, где ':' указывает, что должен быть предоставлен параметр - например. yourFunc(arg1:arg2:)
будет принимать 2 аргумента.
Если внешняя метка не используется, мы помещаем знак подчеркивания ('_').
Для двух приведенных выше функций мы однозначно идентифицируем их, используя:
myFunc(myString:)
и myFunc(_:)