2016-02-21 20 views
5

Tôi có một cái gì đó như thế này:Có thể sử dụng loại siêu dữ liệu (.Type) làm Khóa trong Từ điển không?

class Lumber { } 
class Fruit { } 

enum Size { 
    case Small 
    case Medium 
    case Large 
} 

let lumberSize = [ 
    Size.Small: "2x4", 
    Size.Medium: "4x6", 
    Size.Large: "6x10" 
] 

let fruitSize = [ 
    Size.Small: "grape", 
    Size.Medium: "apple", 
    Size.Large: "watermelon" 
] 

let size:[AnyObject.Type:Dictionary] = [ 
    Lumber.Type: lumberSize, 
    Fruit.Type: fruitSize 
] 

On định nghĩa từ điển size của tôi, tôi nhận được lỗi thời gian thực này từ Xcode Editor:

Loại 'AnyObject.Type' không phù hợp với giao thức ' Hashable '

Bạn có thể nghĩ điều này sẽ giải quyết mọi thứ. Nếu tôi muốn sử dụng X làm khóa trong từ điển và nó không thể băm, thì đơn giản là không thể sử dụng được. Điều đó có ý nghĩa.

Tuy nhiên, có hai điều khiến tôi nghi ngờ thông báo lỗi.

Trước tiên, tại thời điểm này, thông báo lỗi Xcode Editor thời gian thực là khủng khiếp ngoài những điều cơ bản. Nhiều lần mỗi ngày tôi phải bỏ qua những dự đoán của nó về những gì sai và fiddle với cú pháp cho đến khi nó được chấp nhận.

Thứ hai, tôi nghĩ rằng đang đọc các từ trong tài liệu có thể bác bỏ thông báo lỗi. Trong Swift 2.2 Language Reference, dưới loại, nó đọc:

Các metatype của một lớp, loại cấu trúc, hoặc liệt kê là tên của loại tiếp theo .Type

Và trong Swift Standard Library ReferenceCấu trúc ObjectIdentifier Tham chiếu lần đọc:

Trong Swift, chỉ các thể hiện và kiểu dữ liệu lớp mới có các định danh duy nhất.

Và phần đó cũng liệt kê Hashable làm giao thức phù hợp.

Nếu tôi đọc đúng, thì tất cả các loại ObjectIdentifier được Hashable sử dụng. Tôi đã (sai?) Bằng cách sử dụng Comparable làm ví dụ. Chúng ta có thể so sánh các loại vì ObjectIdentifier của chúng phù hợp với Comparable? Kể từ khi ObjectIdentifier phù hợp với Hashable cũng có, sau đó tôi sẽ có thể sử dụng nó trong một từ điển.

Vì vậy, ngay bây giờ tôi nghi ngờ rằng những gì tôi đang có ý định làm là thực sự có thể, nhưng tôi chỉ đơn giản là không thể có được cú pháp chính xác.

Trả lời

7

Hashable là giao thức ObjectIdentifier thực hiện. Điều này có nghĩa là ObjectIdentifier(Lumber.Type) có thể băm, không phải là Lumber.Type. Bạn có thể thử thay đổi mã của bạn để sử dụng ObjectIdentifier, như trong:

class Lumber { } 
class Fruit { } 

enum Size { 
    case Small 
    case Medium 
    case Large 
} 

let lumberSize = [ 
    Size.Small: "2x4", 
    Size.Medium: "4x6", 
    Size.Large: "6x10" 
] 

let fruitSize = [ 
    Size.Small: "grape", 
    Size.Medium: "apple", 
    Size.Large: "watermelon" 
] 

let size:[ObjectIdentifier: [Size: String]] = [ 
    ObjectIdentifier(Lumber): lumberSize, 
    ObjectIdentifier(Fruit): fruitSize 
] 

này biên dịch, nhưng tôi không chắc chắn nếu nó đáp ứng nhu cầu cụ thể của bạn. Cá nhân, tôi sẽ chỉ sử dụng phiên bản chuỗi của tên lớp làm khóa - String(Lumber). tức là:

let size:[String: [Size: String]] = [ 
    String(Lumber): lumberSize, 
    String(Fruit): fruitSize 
] 
+0

Tôi đã hy vọng tránh chuyển đổi Chuỗi nếu chỉ để hiểu sâu hơn về Swift. 1 cho khía cạnh giáo dục. Nếu tôi không biết tôi sẽ làm gì sau cuối tuần tới, tôi sẽ chấp nhận câu trả lời này (hoặc câu trả lời khác). Cảm ơn. – Jeff

Các vấn đề liên quan