Swift中的对象父/子通信

时间:2016-05-05 12:22:55

标签: ios swift

我有一个视图控制器,它包含一些需要相互通信的相关类的实例(对象)。

我可以通过在VC中创建对象的实例来轻松设置它们:

var house = House ()
var road = Road ()
var town = Town ()

但是如何在House对象中获取一个方法来说话' /将数据发送到Road对象?在某些语言中,我可以调用父对象并以这种方式定位其他类及其方法:

func sendHouseData (num: Int) {
_parent.road.getHouseData (num)
}

显然,_parent关键字不是快速代码,因此无法工作。

我能想到的唯一方法是在House对象中创建一个road实例作为子对象,从而将其直接暴露在方法代码的范围内。在VC中有很多外部代码来完成所有繁重工作是另一种看似不好的做法和不优雅的想法。

有什么想法吗?

非常感谢。 千瓦

2 个答案:

答案 0 :(得分:4)

一种方法是使用委托模式。每个类都应该声明一个包含它可以发送的所有消息的协议,需要监听这些消息的类应该实现协议,注册为(或其中一个)委托并做出相应的响应。

以下是如何实施Delegation Pattern的一个很好的例子。

您的对象的示例实现:

protocol HouseDelegate {
    func readData(data:Int)
}

class House {
    var delegate:HouseDelegate
    var data:Int = 0

    init(delegate:HouseDelegate) {
        self.delegate = delegate
    }

    func sendData() {
        self.delegate.readData(data)
    }
}

class Road: HouseDelegate {

    var data:Int = 0
    func readData(data: Int) {
        print("Read data \(data)")
        self.data = data
    }
}

var road = Road ()

var house = House (delegate: road)

house.sendData() //prints "Read data 0"

答案 1 :(得分:1)

处理此问题的最佳方法是使用中介模式,如果您需要在House,Road,Town之间建立通信,则可以通过它们与“中介”(父对象)进行通信的方式进行设置。在这种情况下,父对象可以在对象之间进行调解和协调

或者,您可以使用NSNotificationCenter,从一个对象发布通知并在另一个对象中收听通知,但只要您的应用变得更复杂,就很难跟踪。

假设Word类是House,Road,Town的父类。 在这里,您可以建立Word,House和Town之间的沟通,以及House和Town之间的相互沟通。 请注意,这是更多伪代码我在浏览器中写它但你会明白

class Word {

    let house = House()
    let town = Town()

    init() {
        // Here World will be notified when the house hasReceivedVisitor and the town hasBuiltRoad. 
        self.house.hasReceivedVisitor = { visitorName in 
            print("\(visitorName) has visited the house!")
            // Communication between house and town ...
            self.town.doSometingWithVisitor(visitorName)
        }

        self.town.hasBuiltRoad = { roadNumber in 
            print("A road \(roadNumber) has been built!")
            // Communication between town and house ...
            self.house.doSometingWithRoad(roadNumber)
        }
    }
}

class House {

    var hasReceivedVisitor: ((vistorName: String) -> ())? 

    func createVisitor() {
        let vistor = Visitor("Mike")
        self.hasReceivedVisitor?(vistor.vistorName)
    }

    func doSometingWithRoad(roadNumber: Int) {
        // .....
    }
}

class Town {

    var hasBuiltRoad: ((roadNumber: Int) -> ())?

    func createRoad() {
        let road = Road(66)
        self.hasBuiltRoad?(road.roadNumber)
    }

    func doSometingWithVisitor(visitorName: String) {
        // .....
    }
}

上述同样的事情可以通过委托完成,但我更喜欢块。 基本上你有3个选择:通知(最差),委托或回调。