带有不同签名的Swift下标,用于getter和setter [英] Swift subscript with different signature for the getter and setter

查看:115
本文介绍了带有不同签名的Swift下标,用于getter和setter的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在Swift中是否有subscriptgettersetter签名不同?

Is it possible to have a subscript in Swift that has different signatures for the getter and setter?

例如,我希望getter返回Set<Int>,而setter接受Int(而不是Set<Int>).

For example, I want the getter to return a Set<Int> and the setter to take an Int (not a Set<Int>).

该代码不会编译,但是可以让您了解我要执行的操作:

This code won't compile but it gives you an idea of what I'm trying to do:

struct Foo{

    subscript(index: Int)->String{
        get{
            return "bar" // returns a String
        }
        set(newValue: String?){ // takes a String? instead of a String
            print(newValue)
        }
    }
}

我该怎么做?

推荐答案

这很丑陋,我强烈建议您不要这样做,但是从技术上讲,这是可能的:

This is very ugly, and I strongly discourage you from doing so, but technically this is possible:

struct Foo {

    subscript(concreteValueFor index: Int) -> String {
        return "Get concrete \(index)"
    }

    subscript(optionalValueFor index: Int) -> String? {
        get { return nil }
        set { print("Set optional \(index)") }
    }

}

var foo = Foo()

foo[concreteValueFor: 1]            // Returns "Get concrete 1"
foo[optionalValueFor: 2] = ""       // Prints "Set optional 2"


前段时间,对于多地图,我做了这样的事情:


For a multimap some time ago I made something like this:

public struct Multimap<Key: Hashable, Value: Hashable>: CollectionType {

    public typealias _Element = Set<Value>
    public typealias Element = (Key, _Element)
    public typealias Index = DictionaryIndex<Key, _Element>
    public typealias Generator = DictionaryGenerator<Key, _Element>

    private typealias Storage = [Key: _Element]

    private var storage = Storage()

    public var startIndex: Index { return storage.startIndex }
    public var endIndex: Index { return storage.endIndex }

    public subscript(position: Index) -> _Element { return storage[position].1 }
    public subscript(position: Index) -> Element { return storage[position] }

    subscript(key: Key) -> Set<Value> {
        get { return storage[key] ?? Set<Value>() }
        set { storage[key] = newValue.isEmpty ? nil : newValue }
    }

    public func generate() -> Generator { return storage.generate() }

}

用法:

var foo = Multimap<Int, String>()

foo[0]                      // Returns an emtpy Set<String>
foo[0].insert("Ook")        // Inserts a value at index 0
foo[0].insert("Eek")
foo[0]                      // Now this returns a set { "Ook", "Eek" }
foo[1].insert("Banana")
foo[1].insert("Book")
foo[0].unionInPlace(foo[1])
foo[0]                      // Returns a set { "Banana", "Ook", "Eek", "Book" }

这篇关于带有不同签名的Swift下标,用于getter和setter的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆