hata: yazılabilir atomik özellik, sentezlenmiş bir ayarlayıcı / alıcıyı kullanıcı tanımlı bir ayarlayıcı / alıcı ile eşleyemez


128

Son zamanlarda (eskiden gayet iyi derlemek için kullanılan) eski bir Xcode projesini derlemeye çalıştım ve şimdi bu biçimde birçok hata görüyorum:

error: writable atomic property 'someProperty' cannot pair a synthesized setter/getter with a user defined setter/getter

Bu hatalara neden olan kod kalıbı her zaman şöyle görünür:

// Interface:

@property (retain) NSObject * someProperty;

// Implementation:

@synthesize someProperty; // to provide the getter
- (void)setSomeProperty:(NSObject *)newValue
{
    //..
}

Hatanın neden oluşturulduğunu anlayabiliyorum. Derleyiciye özellik erişimcilerimi (hem alıcı hem de ayarlayıcı) sentezlemesini söylüyorum ve hemen ardından ayarlayıcıyı manuel olarak geçersiz kılıyorum. Bu kod her zaman biraz kötü kokmuştur.

Peki bunu yapmanın doğru yolu nedir? Onun @dynamicyerine kullanırsam @synthesize, alıcıyı da yazmam gerekecek. Tek yol bu mu?


Bu sadece atomicmülklerde mi oluyor ? Atomik özellikler durumunda, kilitleme stratejisi açısından alıcı / ayarlayıcı çiftini senkronize tutmak iyi bir fikir olabilir. Bir parça sentezlenirken diğeri özel kod ise bu zordur.
Nikolai Ruhe

Mülkü atomsuz yaparsam kesinlikle ortadan kalkar. İlginç. Senkronizasyon sorununu düşünmemiştim bile.
James

Tam da bu soruna bir çözüm bulmak için bu konuyu ziyaret ettim. Kendi başıma bir alıcı ve pasör yazmak istemiyorum. Oh peki…
Constantino Tsarouhas

Varsayılan olarak, her özellik atomiktir ve onları açıkça atomik olmayan yapmamız gerekir. Atomik özellikler iş parçacığı açısından güvenlidir, bu nedenle onlar için ayarlayıcı ve alıcı uygulayamayız çünkü iş parçacığı güvenli işlevselliğini değiştirecektir. Umarım bu hatayı almanızın sebebini anlarsınız.
Mohd Haider

Yanıtlar:


218

Aynı sorunu yaşadım ve biraz araştırma yaptıktan sonra, işte bu konuyla ilgili sonucum:

Derleyici sizi @propertyatomik olarak tanımladığınız (yani nonatomicanahtar kelimeyi atlayarak ) konusunda uyarır , ancak bu özelliğe erişimin nasıl senkronize edileceğine dair eksik bir uygulama sağlarsınız.

Bu uyarının ortadan kalkması için:

A'nın @propertyatomik olduğunu ilan ederseniz , aşağıdakilerden birini yapın:

  • @dynamicveya kullanın ;
  • kullanım @synthesizesentezlenmiş ayarlayıcı ve alıcıyı ve saklayın veya;
  • her ikisinin de manuel olarak uygulanmasını sağlar ayarlayıcı hem de alıcı yukarıdaki yönergelerden birini kullanmadan).

Eğer bildirirseniz @propertyile(nonatomic) o zaman Alıcı ve ayarlayıcıların manuel ve sentezlenmiş uygulamaları karıştırabilirsiniz.

Güncelleme: Özelliğin Otomatik Sentezlenmesi Üzerine Bir Not

LLVM 4.0'dan itibaren CLang, olmayan bildirilmiş özellikler için otomatik sentez sağlar @dynamic. Varsayılan olarak, öğesini atlasanız bile @synthesize, derleyici sizin için alıcı ve ayarlayıcı yöntemler sağlayacaktır. Bununla birlikte, atomik özellikler için kural hala aynıdır: Ya derleyicinin hem alıcıyı hem de ayarlayıcıyı sağlamasına izin verin YA DA ikisini de kendiniz uygulayın!


Teşekkürler! "@ özelliğini (
atomsuz

14

Alıcıyı da uygulamanız gerekir. Misal:

// Interface:

@property (retain) NSObject * someProperty;

// Implementation:

- (void)setSomeProperty:(NSObject *)newValue
{
    @synchronized (self)
    {
        // ...
    }
}

- (NSObject *)someProperty
{
    NSObject *ret = nil;

    @synchronized (self)
    {
        ret = [[someProperty retain] autorelease];
    }

    return ret;
}

12

Bu soru, "C hedefi özel özelliği" aramanızdan aldığınız diğer en iyi sonuçların yanı sıra, "setter =" veya "getter =" hakkındaki bilgilerle güncellenmez.

Öyleyse, bu soru hakkında daha fazla bilgi vermek için:

@Property çağrısını kendi yönteminizle yazarak sağlayabilirsiniz.

    @property(setter = MySetterMethod:, getter = MyGetterMethod)

Sağlanan ayarlayıcı yöntemi için iki noktaya dikkat edin.

Başvuru Apple belgeleri

DÜZENLEME: Objective-C'nin özelliklerinde yapılan yeni değişikliklerin (artık çok daha akıllılar) bu sorunun yanıtlarını nasıl değiştirdiğinden emin değilim. Belki de hepsi güncel değil olarak işaretlenmelidir.


Ayarlayıcı yöntemini ayarlamanın aslında uyarıyı kaldırmadığını buldum. örneğin -> "@property (atama, setter = setDelegate :) id delegate;" Bu durumda tek yapabildiğim, kendi alıcımı eklemek veya atomik olmayan özelliği eklemek, yapmam gerekip gerekmediğinden emin değilim, delegeyi kendim 'atomik' olarak ayarladığım için, atomik olmayan özelliğe sahip olmanın önemi yok ya da öyle anlıyorum.
David van Dugteren

İlginç David. Bu Objective-C'nin hangi "sürümü" nde (XCode sürümünün daha yararlı olacağını söylemeyi düşünüyorum)? Özellikle iOS 6 ile Objective-C'de yapılan son değişikliklerin bunu etkilediğinden emin değilim.
Matias Forbord

0

Bu hatayı OP'nin açıkladığı nedenden dolayı almayan diğerleri için, muhtemelen benimle aynı sorunu yaşıyorsunuz:

- () yöntemiyle aynı ada sahip bir @ özelliğiniz var.

Bunun gibi bir şey:

@property UIView *mainView;

-(UIView *)mainView;
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.