2015-07-10 7 views
6

Swift kullanarak bir proje üzerinde çalışıyorum ve Pixel (RGB değerleri gibi renk bilgilerini depolamak için KEY, KEY) ve int değerleri (Değer, sayma için özel bir nesnenin nesneleri saklamak için bir sözlük oluşturmaya çalışıyorum) Aynı görüntüde aynı rengin kaç kez göründüğü). Bu C# iseSwift dilinde Sözlük'te anahtar olmak için özel sınıf tipi nasıl kullanılır?

, çalışma kodu olmalıdır:

Dictionary<Pixel, int> colorDictionary = new Dictionary< Pixel, int>();

Swift, ben denedim:

var colorDictionary = Dictionary<Pixel, Int>() 

Ancak, hata bende:

"Tür 'Piksel' protokole uymuyor 'Hashable'"

Bunu çözmek için ne yapmalıyım? Çok teşekkürler!

+0

Sorun, Andy Ibanez'in ipucu tarafından çözüldü. Ayrıca bu bağlantının faydalı olduğunu da öğrendim: http://www.swiftcoder.info/dev/codefellows/2014/8/2/how-to-implement-hashable-for-your-custom-class –

cevap

3

Sözlük anahtarı kullanmak istediğiniz herhangi bir özel tür, Hashable protokolüyle uyumlu olmalıdır.

Bu protokolde uygulamanız gereken bir özellik vardır.

var hashValue: Int { get }

kullanın bu özellik Sözlükte arama nedenlerle kullanabilirsiniz bir int oluşturmak için. Bunu oluşturmaya çalışmalısınız, böylece oluşturulan hashValue her piksel için benzersizdir.

bir türünün hashValue özelliği tarafından döndürülen değeri arasında aynı olması gerekmez: muhtemelen (sürece benzersiz şekilde) rastgele bir karma yapabilirsiniz

Swift kitabı, aşağıdaki notu vardır Aynı programın farklı uygulamaları veya farklı programlarda. dan Hashable devralır da uygulamak gerekir çünkü o

Not:

func ==(_ lhs: Self, _ rhs: Self) -> Bool. 

Ben senin pikselin iç yapısı ne olduğundan emin değilim, ama muhtemelen her ikisi olduğunda iki piksel eşit düşünebiliriz aynı "x" ve "y" değerleri. Son mantık size kalmış.

istediğiniz kadar bu değiştirin:

struct Pixel : Hashable { 

    // MARK: Hashable 
    var hashValue: Int { 
     get { 
      // Do some operations to generate a unique hash. 
     } 
    } 
} 

//MARK: Equatable 
func ==(lh: Pixel, rh: Pixel) -> Bool { 
    return lh.x == rh.x && rh.y == lh.y 
} 
+0

Açıklama ve aşağıdaki değişiklik çok yararlı! Teşekkürler Andy! Ayrıca aşağıdaki fikirlere katkıda bulunan herkese teşekkür ederiz. –

+0

Andy, şimdi istediğim sözlüğü Pixel türüyle bildirebilirim. Ama Swift'de .contains (Anahtar) adını nasıl kullanacağımı bilmiyorum. Biraz ipucu verebilir misiniz? Teşekkürler! –

+0

Dictionary'ın alt simge operatörü isteğe bağlı olarak döndürür. Sadece iade edilen anahtar nil değilse, kontrol edin veya isteğe bağlı açın. eğer myVal = myDic [anahtar] {...}. –

1

böyle Hashable protokolü uygulamak:

class Pixel : Hashable { 
    var alpha, red, green, blue : Int 

    init(red: Int, green: Int, blue: Int, alpha: Int) { 
     self.red = red 
     self.green = green 
     self.blue = blue 
     self.alpha = alpha 
    } 

    var hashValue : Int { 
     get { 
      return alpha^red^green^blue 
     } 
    } 
} 

func ==(lhs: Pixel, rhs: Pixel) -> Bool { 
    return lhs.alpha == rhs.alpha && lhs.red == rhs.red && lhs.green == rhs.green && lhs.blue == rhs.blue 
} 
3

Andy Ibanez yayınlanmıştır ne Devam edersek. HashValue uygulamasının kısayolu, String'in hashValue'sini dağıtmaktır. Böyle bir şey yapabilirsin. Bu durumda hashValues ​​sadece iki nesneyi doğrulamak için hızlı bir kontrol vardır eşit değildir çünkü

class Pixel: Hashable { 
    var r:Int = 0; 
    var g:Int = 0; 
    var b:Int = 0; 
    var a:Int = 0; 

    var hashValue: Int { 
     get { 
      return "\(r)\(g)\(b)\(a)".hashValue; 
     } 
    } 
} 

Ayrıca, bir Equatable işlev gerekir. İki nesnenin aynı hashValue'ye sahip olması, ancak eşit olmaması mümkün olduğundan, aşağıdaki gibi eşitliği tanımlamak için hala == değerini uygulamanız gerekir.

func ==(lhs: Pixel, rhs: Pixel) -> Bool{ 
    if lhs.r != rhs.r{ 
     return false; 
    } 
    if lhs.g != rhs.g{ 
     return false; 
    } 
    if lhs.b != rhs.b{ 
     return false; 
    } 
    if lhs.a != rhs.a{ 
     return false; 
    } 
    return true; 
} 
+1

Clever! Bunu bir sebepten dolayı düşünmemiştim. –

İlgili konular