Подтвердить что ты не робот

Что такое "я", используемое в Swift?

Я новичок в Swift, и мне интересно, для чего используется self и почему.

Я видел это в классах и структурах, но я действительно не считаю их существенными и необходимыми, чтобы даже упомянуть их в моем коде. Для чего они нужны и почему? В каких ситуациях это необходимо использовать?

Я читал много вопросов и ответов для этого вопроса, но никто из них не полностью отвечает на мои вопросы, и они всегда склонны сравнивать его с this, как на Java, с которым я не знаком вообще.

4b9b3361

Ответ 1

Вы также будете использовать себя при создании своих расширений, например:

extension Int {
    func square() -> Int {
        return self * self
    }

    // note: when adding mutating in front of it we don't need to specify the return type
    // and instead of "return " whatever
    // we have to use "self = " whatever

    mutating func squareMe() {
        self = self * self
    }
}
let x = 3
let y = x.square()  
println(x)         // 3
printlx(y)         // 9

теперь позволяет сказать, что вы хотите изменить сам результат var вы должны использовать mutating func, чтобы самому внести изменения.

var z = 3

println(z)  // 3

теперь позволяет мутировать его

z.squareMe()

println(z)  // 9

//теперь можно увидеть другой пример, используя строки:

extension String {
    func x(times:Int) -> String {
        var result = ""
        if times > 0 {
            for index in 1...times{
                result += self
            }
            return result
        }
        return ""
    }

    // note: when adding mutating in front of it we don't need to specify the return type
    // and instead of "return " whatever
    // we have to use "self = " whatever

    mutating func replicateMe(times:Int){
        if times > 1 {
            let myString = self
            for index in 1...times-1{
                self = self + myString
            }
        } else {
            if times != 1 {
                self = ""
            }
        }
    } 
}


var myString1 = "Abc"
let myString2 = myString1.x(2)

println(myString1)         // "Abc"
println(myString2)         // "AbcAbc"

теперь позволяет изменять myString1

myString1.replicateMe(3)

println(myString1)         // "AbcAbcAbc"

Ответ 2

Обновление: 24 ноября 2015 г.

Да, это то же самое, что this в Java и self в Objective-C, но с Swift, self требуется только, когда вы вызываете свойство или метод из закрытия или различаете имена свойств внутри вашего кода (например, инициализаторы). Таким образом, вы можете безопасно использовать почти все ваши компоненты класса без использования "я", если вы не вызываете вызов из закрытия.

"Свойство self Каждый экземпляр типа имеет неявное свойство называется self, что в точности эквивалентно самому экземпляру. Вы используйте свойство self, чтобы ссылаться на текущий экземпляр внутри его собственные методы экземпляра.

Метод increment() в приведенном выше примере может быть написан например:

func increment() {
    self.count++
}

На практике вам не нужно писать self в свой код очень часто. Если вы явно не пишете self, Swift предполагает, что вы ссылаясь на свойство или метод текущего экземпляра всякий раз, когда вы используйте известное свойство или имя метода в рамках метода. Это предположение демонстрируется использованием count (а не self.count) внутри трех методов экземпляра для счетчика.

Основное исключение из этого правила возникает, когда имя параметра для метод экземпляра имеет то же имя, что и свойство этого экземпляра. В в этой ситуации имя параметра имеет приоритет, и оно становится необходимо ссылаться на имущество более квалифицированным образом. Ты используешь свойство self, чтобы различать имя параметра и имя свойства.

Здесь self устраняет неоднозначность между параметром метода с именем x и свойство экземпляра, которое также называется x: "

Отрывок из: Apple Inc. "Быстрый язык программирования (Swift 2 Preerelease)".


Вот как Ray Wenderlich рекомендует использовать self в Swift для своих обучающих программ:

Использование Self

Для краткости избегайте использования self, так как Swift не требует, чтобы он обращался к свойствам объекта или вызывал его методы.

Используйте self, если требуется, чтобы различать имена свойств и аргументы в инициализаторах и при ссылках на свойства в выражениях закрытия (как требуется компилятору):

class BoardLocation {
  let row: Int, column: Int

  init(row: Int, column: Int) {
    self.row = row
    self.column = column

    let closure = {
      println(self.row)
    }
  }
}

И это GitHub рекомендации для self для своих приложений:

При необходимости явно ссылайтесь на self

При доступе к свойствам или методам в self по умолчанию оставить ссылку на self неявным:

private class History {
    var events: [Event]

    func rewrite() {
        events = []
    }
}

Включать только явное ключевое слово, когда требуется язык, например, в закрытии или конфликты параметров:

extension History {
    init(events: [Event]) {
        self.events = events
    }

    var whenVictorious: () -> () {
        return {
            self.rewrite()
        }
    }
}

Обоснование: это делает захватывающую семантику самооценки больше в закрытии и избегает многословия в другом месте.

Ответ 3

В каких ситуациях необходимо использовать его

Необходимо использовать его только тогда, когда имя локальной переменной затмевает имя свойства.

Однако, в зависимости от стиля (и читаемости), я всегда использую его:

  • Я использую его с именами свойств, потому что в противном случае мне остается недоумевать, что это за переменная (поскольку она не объявлена ​​ни локально, ни входящим параметром).

  • Я использую его как получатель вызовов функции (метода), чтобы отличать такие методы от функций верхнего уровня или локальных.

Ответ 4

Я собираюсь рассказать о том, зачем нам self.

Когда мы определяем класс, например:

class MyClass {
    func myMethod()
}

Мы создаем объект класса. Да, класс тоже объект.

Тогда независимо от того, сколько экземпляров создается с помощью класса, все экземпляры будут иметь ссылку на свой объект класса.

Вы можете представить, что все методы экземпляров, определенные классом, находятся в объекте класса, и их будет только одна копия.

enter image description here

Это означает, что все экземпляры, созданные с использованием класса, используют один и тот же метод.

Теперь, представляя, что вы являетесь myMethod в объекте класса, и потому, что вы являетесь общим для всех экземпляров, вы должны иметь способ сообщить, в каком экземпляре вы работаете.

Когда кто-то говорит instance1.myMethod(), это означает "Привет! myMethod, выполните свою работу, а instance1 - объект, над которым вы работаете".

Как вы ссылаетесь на объект, который отправил вам вызывающий, используйте self.

Исправьте меня, если я ошибаюсь, спасибо.

"На практике вам не нужно писать себя в свой код очень часто. вы явно не пишете себя, Свифт предполагает, что вы ссылаетесь к свойству или методу текущего экземпляра всякий раз, когда вы используете известное свойство или имя метода в рамках метода.

Отрывок из: Apple Inc." Быстрый язык программирования ". интерактивные книги. https://itun.es/tw/jEUH0.l

Ответ 5

Прежде всего: хорошие ответы, примеры и объяснения, уже размещенные здесь, хотя я должен указать что-то:

Зарезервированное слово: self в swift похоже на this , но это не то же самое, что в Java или Javascript.

Как правильно цитировал @Dave Gomez:

Каждый экземпляр типа имеет неявное свойство, называемое self, которое в точности эквивалентно самому экземпляру.

И здесь начинается одно из основных различий, потому что:

  • "Каждый экземпляр" в быстром (по крайней мере на данный момент) почти все
  • Когда в Java (например) вы можете использовать только слово this внутри области экземпляра, в swift вы можете использовать его почти Every-where

Вот несколько примеров:

//Example 1:
var x="foo"
x.self="bar".self//compiles and run

//Example 2:
print.self(x);//compiles and run

//Example 3:
func myOther(self otherSelf:Person){}
myOther(self: personObject);//compiles and run

//Example 4:
class Foo{
      var bar=""
      init(){
          self.addSome()//this would be the same in Java
      }
      func addSome(){
          //But definitely not this:
          self.self.bar.self.self="some".self.self
      }
}
//Guess what - also compiles and run...
let f=Foo()
print(f.bar)

Если вы хотите больше узнать, посмотрите: Почему "self.self" компилируется и запускается в быстром

Вопрос OP о том, что он в быстром, поэтому я не буду читать читателей с объяснениями, что это на Java или Javascript (но если некоторым читателям нужно просто написать комментарий).

Ответ 6

В следующей статье подробно описывается self:

Как правильно использовать ключевое слово self в Swift


self является свойством экземпляра, который ссылается на себя. Он использовался для доступа к экземпляру класса, структуры и перечисления в рамках методов.

Когда пользователь получает доступ к типу метода (static func или class func), он ссылается на фактический тип (а не на экземпляр).

Swift позволяет пропустить self, когда вы хотите получить доступ к свойствам экземпляров.

Если параметр метода имеет то же имя, что и свойство экземпляра, вы должны явно использовать self.myVariable = myVariable для проведения различия. Обратите внимание, что параметры метода имеют приоритет над свойствами экземпляра.

Ответ 7

Я - это свойство экземпляра, которое ссылается на себя. Он используется для доступа к классу, структуре и экземпляру перечисления внутри методов. Когда параметр метода имеет то же имя, что и свойство экземпляра, вы должны явно использовать self.myVariable = myVariable, чтобы провести различие. Обратите внимание, что параметры метода имеют приоритет над свойствами экземпляра.

    struct Weather {
let windSpeed: Int
  let chanceOfRain: Int
  init(windSpeed: Int, chanceOfRain: Int) {
    self.windSpeed = windSpeed
    self.chanceOfRain = chanceOfRain
  }

  func isDayForWalk() -> Bool {
    let comfortableWindSpeed = 5
    let acceptableChanceOfRain = 30
    return self.windSpeed <= comfortableWindSpeed
      && self.chanceOfRain <= acceptableChanceOfRain
  }

}
// A nice day for a walk
let niceWeather = Weather(windSpeed: 4, chanceOfRain: 25)  
print(niceWeather.isDayForWalk()) // => true

Ответ 8

Я пришел к этому вопросу (& ответы), когда искал self как функцию класса, которая выглядит следующим образом: Int.self, String.self или YourClass.self

Ранее, насколько я могу судить, только Дмитрий Павлутин отвечает на этот вопрос, когда говорит:

Когда к self обращаются в методе типа (статический func или class func), он ссылается на фактический тип (а не на экземпляр).

Когда self используется таким образом, он фактически возвращает то, что в Swift называется метатипом. Вы можете прочитать документацию об этом здесь: https://docs.swift.org/swift-book/ReferenceManual/Types.html#//apple_ref/swift/grammar/metatype-type

На swiftrocks.com есть также очень хорошая статья с примерами об использовании метатипов.