2016-06-19 5 views
0

私の辞書のキーに使用されるハッシュ値を構築したいと思います。 2つの文字列とNSDateを持つ構造体で構成されていなければなりません。私は私が正しく以下の私のhashValueゲッターを建てわからない:私の辞書のためのカスタムハッシュ可能な構造体

// MARK: comparison function for conforming to Equatable protocol 
func ==(lhs: ReminderNotificationValue, rhs: ReminderNotificationValue) -> Bool { 
    return lhs.hashValue == rhs.hashValue 
} 
struct ReminderNotificationValue : Hashable { 
    var notifiedReminderName: String 
    var notifiedCalendarTitle: String 
    var notifiedReminderDueDate: NSDate 

var hashValue : Int { 
    get { 
     return notifiedReminderName.hashValue &+ notifiedCalendarTitle.hashValue &+ notifiedReminderDueDate.hashValue 
    } 
} 

init(notifiedReminderName: String, notifiedCalendarTitle: String, notifiedReminderDueDate: NSDate) { 
    self.notifiedReminderName = notifiedReminderName 
    self.notifiedCalendarTitle = notifiedCalendarTitle 
    self.notifiedReminderDueDate = notifiedReminderDueDate 
} 
} 


var notifications: [ReminderNotificationValue : String] = [ : ] 

let val1 = ReminderNotificationValue(notifiedReminderName: "name1", notifiedCalendarTitle: "title1", notifiedReminderDueDate: NSDate()) 
let val2 = ReminderNotificationValue(notifiedReminderName: "name1", notifiedCalendarTitle: "title1", notifiedReminderDueDate: NSDate()) 

notifications[val1] = "bla1" 
notifications[val2] = "bla2" 

notifications[val2] // returns "bla2". 
notifications[val1] // returns "bla1". But I'd like the dictionary to overwrite the value for this to "bla2" since val1 and val2 should be of equal value. 

答えて

1

問題はあなたのhashValue実装が、==関数ではありません。 一般に、x == yは、x.hashValue == y.hashValueを意味しますが、ではなく、 です。異なるオブジェクトは同じハッシュ値を持つことができます。 はさえ

var hashValue : Int { return 1234 } 

は無効が、有効ハッシュ方式になります。

したがって==で、あなたは正確な 平等のための2つのオブジェクトを比較する必要があります。

func ==(lhs: ReminderNotificationValue, rhs: ReminderNotificationValue) -> Bool { 
    return lhs.notifiedReminderName == rhs.notifiedReminderName 
    && lhs.notifiedCalendarTitle == rhs.notifiedCalendarTitle 
    && lhs.notifiedReminderDueDate.compare(rhs.notifiedReminderDueDate) == .OrderedSame 
} 

あなたのコード内の別の問題は、NSDateは絶対 あるよう NSDate()の2つの呼び出しは、異なる日付を作成することです浮動小数点数として表現され、小秒の の精度で表されます。

+0

ありがとうございました。実際には、私は同じ日を渡す場合、期待された動作が動作するようです。私の==関数でさえ。何故ですか? – Daniel

+0

@ダニエル:それは偶然に動作します。文字列のハッシュ値は64ビットの数値なので、すべての文字列が同じハッシュを持つわけではありません。しかし、同じハッシュを持つ2つの文字列の実際の例を見つけるのは難しいかもしれません。 - たとえば、NSArrayはハッシュとして要素の数だけを使用することに注意してください。 –

+0

どのくらい試しても、元の実装では正常に動作します。私はあなたの解決策を受け入れ、それに感謝します。しかし、私はちょうど私が異なるテストケースでそれを試しても、なぜうまくいかないものがうまくいくのか理解したいだけです。 – Daniel

関連する問題