如何将AnyClass转换为特定的类并在Swift中动态初始化它?

时间:2014-06-09 11:38:12

标签: swift

Object-C 中,我将Class对象存储在一个数组中并像这样动态地启动它们:

self.controllers=@[[OneViewController class],[TwoViewController class]];
Class clz = self.controllers[index];
UIViewController *detailViewController = [[clz alloc] init];

Swift 中我尝试这种方式,但它会引发错误:

var controllers:AnyClass[] = [OneViewController.self,TwoViewController.self]
var clz : AnyClass = controllers[index]
var instance = clz() // Error:'AnyObject' is not constructible with ()

我想知道是否有办法将AnyClass转换为特定的类? 还是其他任何好主意?

5 个答案:

答案 0 :(得分:52)

您可以将数组指定为公共超类的类型,然后类型演绎做正确的事(Beta-3语法):

let classArray: [UIViewController.Type] = [
    OneViewController.self, TwoViewController.self
]
let controllerClass = classArray[index]
let controller = controllerClass.init()

答案 1 :(得分:9)

我找到了解决这个问题的方法:

var controllers:AnyClass[] = [OneViewController.self,TwoViewController.self]
var clz: NSObject.Type = controllers[0] as NSObject.Type
var con = clz()

记得在ViewController类中添加@objc

答案 2 :(得分:9)

首先必须将AnyClass变量转换为特定类型才能初始化实例:

// Code checked to run on xCode 7.1.1
import UIKit

var aClass: AnyClass = UIButton.self

// Error: 'init' is a member of the type...
// let doesNotWork = aClass.init()

// aClass must be casted first
var buttonClass = aClass as! UIButton.Type
var oneButton = buttonClass!.init()
var otherButton = buttonClass!.init(frame: CGRectZero)

答案 3 :(得分:5)

这是动态类类型的纯粹快速实现。它确实需要类扩展相同的协议。

protocol ILayout{ init(_ a:String)}   
class A:ILayout{required init(_ a:String)}  
class B:ILayout{required init(_ a:String)}   
var instance:ILayout   
var classType:ILayout.Type

classType = A.self   
instance = classType.init("abc")

classType = B.self   
instance = classType.init("abc")

答案 4 :(得分:0)

如果这些类都是Objective-C NSObject 子类,你可以这样做(是的,反引号是有意的):

var constructors: (Void -> NSObject!)[] = [ NSMutableString.`new`, NSMutableArray.`new`, NSMutableDictionary.`new` ]

let string = constructors[0]()
(string as NSMutableString).appendString("Hello")

let array = constructors[1]()
(array as NSMutableArray).addObject("Swift")

let dictionary = constructors[2]()
(dictionary as NSMutableDictionary).setObject("Objective-C", forKey: "Goodbye")

NSLog("dynamically created a string: \(string), an array: \(array), and a dictionary: \(dictionary)")

应输出:

dynamically created a string: Hello, an array: (
    Swift
), and a dictionary: {
    Goodbye = "Objective-C";
}

在我看来应该有更优雅的方式来做到这一点。