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

Свойства вложенных свойств Swift

Быстро ли нет вложенных классов?

Например, я не могу получить доступ к тесту свойств мастер-класса из вложенного класса.

class master{
  var test = 2;

  class nested{
     init(){
       let example = test; //this doesn't work
     }
   }
 }
4b9b3361

Ответ 1

Вложенные классы Swift не похожи на вложенные классы Java. Ну, они похожи на один вид Java-вложенных классов, но не тот вид, о котором вы думаете.

В Java экземпляр внутреннего класса автоматически ссылается на экземпляр внешнего класса (если только внутренний класс не объявлен static). Вы можете создать экземпляр внутреннего класса, если у вас есть экземпляр внешнего класса. Вот почему в Java вы говорите что-то вроде this.new nested().

В Swift экземпляр внутреннего класса не зависит от любого экземпляра внешнего класса. Это как будто все внутренние классы в Swift объявлены с помощью Java static. Если вы хотите, чтобы экземпляр внутреннего класса имел ссылку на экземпляр внешнего класса, вы должны сделать его явным:

class Master {
    var test = 2;

    class Nested{
        init(master: Master) {
            let example = master.test;
        }
    }

    func f() {
        // Nested is in scope in the body of Master, so this works:
        let n = Nested(master: self)
    }
}

var m = Master()
// Outside Master, you must qualify the name of the inner class:
var n = Master.Nested(master:m)

// This doesn't work because Nested isn't an instance property or function:
var n2 = m.Nested()

// This doesn't work because Nested isn't in scope here:
var n3 = Nested(master: m)

Ответ 2

Это решение похоже на то, как я его использую в С#, и я успешно протестировал его в Xcode.

Здесь разбивка процесса:

  • Ваш вложенный класс должен быть необязательным, поэтому вам не нужно его инициализировать, поэтому theres '?' в декларации; если вы инициализируете как родительский класс, так и ваш вложенный класс, вы получаете эффект "рекурсии" и генерируется ошибка.
  • Создайте регулярную функцию, которая получает аргумент того же типа, что и ваш основной класс
  • Передайте этот аргумент вашему вложенному классу (это может перейти в нормальный инициализатор вложенного объекта). - Поскольку объекты по умолчанию передаются по ссылке, нет ничего особенного, чтобы ваш вложенный класс мог ссылаться на родительский класс
  • Внутри вашего вложенного класса вам нужна переменная того же типа, что и родительский класс

Здесь вы можете настроить все, как обычно.

В области выполнения кода ваш вложенный объект класса также должен рассматриваться как необязательный (отсюда и "?" ). Если вы забудете об этом, Xcode добавит его в любом случае.

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

testClass.set.(and then a descriptive method name)

Вот код, и его цель - вывести "тест" в консоли, после того, как значение установлено через вложенный объект:

class testClass
{
    var test_string:String = ""
    var set: class_set?

    func construct_objects(argument: testClass)
    {
        self.set = class_set(argument: argument)
    }
    class class_set
    {
        var parent:testClass
        init(argument: testClass)
        {
            parent = argument
        }
        func test_string_to_argument(argument: String)
        {
            parent.test_string = argument
        }
    }
}
var oTestClass = testClass()
oTestClass.construct_objects(oTestClass)
oTestClass.set?.test_string_to_argument("test")
print(oTestClass.test_string)