Swift-在班级中引用班级的类型

时间:2018-07-05 23:55:05

标签: swift

在使用静态类型时,从类型的实例方法中键入属性和方法,我经常重复使用该类型的名称。

例如

class Foo
{
    // Type properties, methods

    static let kBrandColor = UIColor.red
    static let kMeaning = 42

    static func makeThing() -> Thing { ... }

    // Instance method

    func printStuff()
    {
        print("Brand Color is: \(Foo.kBrandColor)")
        print("The meaning of life is: \(Foo.kMeaning)")

        let thing = Foo.makeThing()
        print("Thing is \(thing)"
    }

    ...
}

这些对“ Foo”的重复引用可能(并且经常如此)导致复制粘贴,重构时出现错误。忘记更改“ Foo”很容易,并且代码仍然可以编译。

所以,我一直在使用这样的模式:

class Foo
{
    fileprivate typealias _ThisClass = Foo

    // Type properties, methods

    static let kBrandColor = UIColor.red
    static let kMeaning = 42

    static func makeThing() -> Thing { ... }

    // Instance method

    func printStuff()
    {
        print("Brand Color is: \(_ThisClass.kBrandColor)")
        print("The meaning of life is: \(_ThisClass.kMeaning)")

        let thing = _ThisClass.makeThing()
        print("Thing is \(thing)"
    }

    ...
}

此方法具有一定的复制和粘贴安全性,但以牺牲一些样板为代价。

是否有更好,更清洁的解决方案来解决此问题? (我曾尝试过搜索SO,但要针对此类问题正确找到搜索字词就很棘手。)

2 个答案:

答案 0 :(得分:0)

协议在这里可以很好地工作。您可以定义协议所需的属性,然后将其应用于要在其中使用这些属性的任何类。

protocol Brandable {
    var kBrandColor: UIColor { get }
    var kMeaning: Int { get }
}

class Foo: Brandable {
    let kBrandColor: UIColor = .red
    let kMeaning: Int = 42
}

如果要重用printStuff函数,还可以将其放入协议中,并将基本实现放入扩展中:

protocol Brandable {
    var kBrandColor: UIColor { get }
    var kMeaning: Int { get }

    func printStuff()
}

extension Brandable {
    func printStuff() {
        print("Brand Color is: \(kBrandColor)")
        print("The meaning of life is: \(kMeaning)")
    }
}

class Foo: Brandable {
    let kBrandColor: UIColor = .red
    let kMeaning: Int = 42
}

class Bar: Brandable {
    let kBrandColor: UIColor = .blue
    let kMeaning: Int = 100
}

Foo().printStuff()
Bar().printStuff()

可以使用makeStuff()函数完成相同的操作。共享功能包含在协议及其扩展中。如果需要更改某些类的行为,则只需添加自己的printStuff或makeStuff函数即可覆盖协议的默认实现。

答案 1 :(得分:0)

使用Identifiable属性创建类似identifier的协议。然后使您想要可识别的任何类都符合它。这是面向协议的方法。

protocol Identifiable {
    static var identifier: String { get }
}
extension Identifiable {
    static var identifier: String {
        return String(describing: self)
    }
}

class X: Identifiable {}

您也不需要引用类名。只需致电type(of: instance).identifier

相关问题