为什么协议类型永远不会得到值?

Why protocol type never gets a value?

我正在尝试了解更多协议。我无法弄清楚 myProtocolFunction 从不调用和打印或传递变量,如下所示。

我认为我的问题是关于初始化的。当我尝试使用两个 viewcontroller 时,一切正常,但 MyStruct 协议实例为零。感谢您的帮助。

class ViewController: UIViewController, MyProtocol {
    var myProtocolValue: String = ""
    
    var globalInstance = "a"

    override func viewDidLoad() {
        super.viewDidLoad()
                
    }
    
    
    @IBAction func click(_ sender: Any) {
        
        var myStruct = MyStruct()
        myStruct.myProtocol = self        
    }
    

    func myProtocolFunction(passing: String) {
        globalInstance = passing
        print("never print")
    }
}

protocol MyProtocol {
    func myProtocolFunction(passing: String)
}


struct MyStruct {

    var myProtocol: MyProtocol?
    
    init() {
        makeSomething()
    }
    
    func makeSomething() {
        myProtocol?.myProtocolFunction(passing: "abc")
        
    }
}

1- 你需要

var myStruct = MyStruct() // an instance variable 

@IBAction func click(_ sender: Any) {
    
    myStruct.myProtocol = self        
}

2- 你甚至在你设置 myProtocol 之前调用 init 当你做 var myStruct = MyStruct() 时调用它,那时 myProtocol 是零,因为它还没有设置

init() {
    makeSomething()
}

检查完整的工作编辑

class ViewController: UIViewController, MyProtocol {

    override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view.
        
    }
    
    func myProtocolFunction(passing: String) {
        print(passing)
    }
     
    @IBAction func click(_ sender: Any) {
          
        var myStruct = MyStruct(self)
        
    }
     
}

protocol MyProtocol {
    func myProtocolFunction(passing: String)
}

struct MyStruct {

    var myProtocol: MyProtocol?
    
    init(_ mine:MyProtocol) {
        myProtocol = mine
        makeSomething()
    }
    
    func makeSomething() {
        myProtocol?.myProtocolFunction(passing: "abc")
        
    }
}

protocols 视为一种类型,在您的结构中,您基本上是在说 这个结构有一个这种类型的变量(你的协议) 在 init 上,您正在尝试调用它的函数。

您缺少的是设置类型实例(您的协议) 所以它可以被调用。

例如:

MyStruct = MyStruct(myProtocol: ViewController())

现在你的可空协议有一个值并且可以调用它的函数,换句话说,协议不能直接在它们中实现它们更像是一个签名合约

详细了解协议 here

您需要在点击操作之外创建 MyStruct() 对象,否则当范围超过您的对象时,您的对象将被取消初始化。

此外,您必须在按钮单击时调用 .makeSomething() 函数,因为对象创建委托的时间为零。

var myStruct = MyStruct() // Create an instance here

@IBAction func click(_ sender: Any) {
    myStruct.myProtocol = self        
// Add your action
    myStruct.makeSomething()
}