Objective-C'de kategorileri kullanarak yöntemleri geçersiz kılma


87

Zaten bir kategori kullanılarak uygulanmış bir yöntemi geçersiz kılmak için bir sınıf kategorisi kullanabilir miyim? Bunun gibi:

1) Orijinal yöntem

-(BOOL) method {
  return true;
}

2) Geçersiz kılınan yöntem

-(BOOL) method {
  NSLog(@"error?"); 
  return true; 
}

Bu işe yarayacak mı yoksa yasa dışı mı?

Yanıtlar:


147

Gönderen Elma belgelerinde :

Objective-C dili şu anda sınıfın devraldığı yöntemleri veya hatta sınıf arabiriminde bildirilen yöntemleri geçersiz kılmak için bir kategori kullanmanıza izin verse de , bunu yapmaktan kesinlikle vazgeçersiniz . Bir kategori, bir alt sınıfın yerine geçmez. Yöntemleri geçersiz kılmak için bir kategori kullanmanın birkaç önemli eksikliği vardır:

  • Bir kategori miras alınan bir yöntemi geçersiz kıldığında, kategorideki yöntem her zamanki gibi miras alınan uygulamayı bir mesaj yoluyla çağırabilir super. Bununla birlikte, bir kategori, kategorinin sınıfında bulunan bir yöntemi geçersiz kılarsa, orijinal uygulamayı çağırmanın bir yolu yoktur .

  • Bir kategori, aynı sınıfın başka bir kategorisinde bildirilen yöntemleri güvenilir bir şekilde geçersiz kılamaz.

    Kakao sınıflarının çoğu kategoriler kullanılarak uygulandığı için bu konu özellikle önemlidir. Geçersiz kılmaya çalıştığınız çerçeve tanımlı bir yöntemin kendisi bir kategoride uygulanmış olabilir ve bu nedenle hangi uygulamanın öncelikli olduğu tanımlanmamıştır.

  • Bazı kategori yöntemlerinin varlığı, tüm çerçevelerde davranış değişikliklerine neden olabilir. Örneğin, windowWillClose:NSObject üzerindeki bir kategorideki temsilci yöntemini geçersiz kılarsanız, programınızdaki tüm pencere temsilcileri daha sonra kategori yöntemini kullanarak yanıt verir; NSWindow'daki tüm örneklerinizin davranışı değişebilir. Bir çerçeve sınıfına eklediğiniz kategoriler, davranışta gizemli değişikliklere ve çökmelere neden olabilir.


Teşekkür ederim ama bunu zaten biliyorum. Davamın yasal olup olmadığını merak ediyorum. Benim durumum belgelerden biraz farklı. :)
retix

Neden farklı? Doküman, orijinal yöntemin bir kategoride olmaması, ancak kesinlikle önerilmemesi durumunda yasal olduğunu söylüyor. O zaman yapabilirsin ...
Benoît

1
Tavsiye için teşekkür ederim. Bu dilde fakirim. Senden yeni bilgiler aldım.
retix

1
Süper sınıfın Kategorisinde bildirilen ve uygulanan Kategori yönteminde geçersiz kılma doğru mudur?
BergP



9

Eski dokümantasyon bağlantısı kesildi; bulabildiğim en iyi yedek buradaydı: Apple Docs :

Kategori Yöntem Adı Çakışmalarından Kaçının

Bir kategoride bildirilen yöntemler var olan bir sınıfa eklendiğinden, yöntem adları konusunda çok dikkatli olmanız gerekir.

Bir kategoride bildirilen bir yöntemin adı, orijinal sınıftaki bir yöntemle veya aynı sınıftaki (veya hatta bir üst sınıf) başka bir kategorideki bir yöntemle aynıysa, davranış, hangi yöntem uygulamasının kullanılacağı konusunda tanımsızdır. Çalışma süresi. Kendi sınıflarınızla kategorileri kullanıyorsanız, bu daha az sorun yaratır, ancak standart Cocoa veya Cocoa Touch sınıflarına yöntemler eklemek için kategorileri kullanırken sorunlara neden olabilir.

Apple daha hafif bir dokunuş kullanıyor, ancak ana nokta aynı: felaketi davet ediyorsunuz, çünkü öngörülemeyen davranış sessiz.


2

Bir kategorinin, temel sınıftaki mevcut yöntemleri geçersiz kılmak için de kullanılabileceğini unutmamak önemlidir (örneğin, Car sınıfının sürücü yöntemi), ancak bunu asla yapmamalısınız. Sorun, kategorilerin düz bir organizasyon yapısı olmasıdır. Car + Maintenance.m'de mevcut bir yöntemi geçersiz kılar ve ardından davranışını başka bir kategoriyle tekrar değiştirmek istediğinize karar verirseniz, Objective-C'nin hangi uygulamayı kullanacağını bilmesinin bir yolu yoktur. Alt sınıflandırma, böyle bir durumda neredeyse her zaman daha iyi bir seçenektir.

Bu eğiticiden, http://rypress.com/tutorials/objective-c/categories

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.