Célkitűzés-C

Célkitűzés-C
Nyelvóra objektum-orientált , több paradigma : tükröző-orientált
Megjelent 1983
Szerző Brad Cox
Fájlkiterjesztés _ .h, .m, .mmvagy.C
Kiadás
Típusrendszer gyenge , statikus / dinamikus
Főbb megvalósítások Kakaó , Cocoa Touch , gcc , LLVM + Clang
Befolyásolva Smalltalk , C
befolyásolta Java , Objective-J , Swift
Weboldal developer.apple.com/libr…
 Médiafájlok a Wikimedia Commons oldalon

Az Objective-C  az Apple Corporation által használt lefordított objektum-orientált programozási nyelv , amely a C nyelvre és a Smalltalk paradigmákra épül . Konkrétan az objektummodell Smalltalk stílusban épül fel – vagyis üzeneteket küldenek az  objektumoknak .

Az Objective-C nyelv a C nyelv szuperkészlete , így a C kód teljesen érthető az Objective-C fordító számára.

Az Objective-C fordító a GCC része, és a legtöbb nagyobb platformon elérhető. A nyelvet elsősorban a Mac OS X ( Cocoa ) és a GNUstep operációs rendszerekhez használják, amelyek az OpenStep  objektumorientált felület megvalósításai . A nyelvet az iOS ( Cocoa Touch ) is használja.

Történelem

Az 1980-as évek elején a strukturált programozás népszerű volt , lehetővé téve az algoritmusok kis blokkokra való felosztását. A feladatok egyre összetettebbé válásával azonban a strukturált programozás a kód minőségének csökkenéséhez vezetett. Egyre több olyan függvényt kellett írnunk, amit más programokban nagyon ritkán lehetett használni.

Sok programozó az objektum-orientált programozásban látott lehetséges megoldást problémájára. Egyrészt a Smalltalkot szinte minden többé-kevésbé bonyolult rendszer használta. Másrészt a virtuális gépek használata megnövelte az erőforrásigényt.

Az Objective-C-t Brad Cox hozta létre az 1980-as évek elején a Stepstone nevű cégénél . Megpróbálta megoldani a kód újrafelhasználásának problémáját.

Cox célja egy olyan nyelv létrehozása volt, amely támogatja a szoftveres IC koncepcióját, amely magában foglalja a programok kész komponensekből (objektumokból) való összeállításának lehetőségét, ahogyan összetett elektronikus eszközöket is össze lehet állítani kész integrált áramkörökből .

Ugyanakkor a nyelvnek egyszerűnek kell lennie, és a C nyelven kell alapulnia, hogy megkönnyítse a fejlesztők átállását arra.

Az egyik cél egy olyan modell létrehozása is volt, amelyben maguk az osztályok is teljes értékű objektumok, támogatva lenne az introspekció és a dinamikus üzenetfeldolgozás.

Az Objective-C a C kiterjesztése: bármely C program egy Objective-C program.

Az Objective-C egyik jellemzője, hogy dinamikus: a fordítási időben általában meghozott döntések a futásidőre halaszthatók.

Az Objective-C egy üzenet-orientált nyelv, míg a C++ funkció-orientált: az Objective-C-ben a metódushívások nem függvényhívásként értelmeződnek (bár általában ez jön le), hanem üzenetként (egy név és argumentumok) objektum, akárcsak a Smalltalkban.

Bármely objektum bármilyen üzenetet elküldhet. Egy objektum ahelyett, hogy egy üzenetet feldolgozna, továbbíthatja azt egy másik objektumnak feldolgozásra (delegálásra), így különösen elosztott (vagyis különböző címterekben és akár különböző számítógépeken elhelyezkedő) objektumokat valósíthat meg.

Egy üzenet hozzárendelése a megfelelő függvényhez futás közben történik.

Az Objective-C nyelv támogatja a metainformációkkal való munkát  - például futás közben megtudhatja egy objektum osztályát, metódusainak listáját (az átadott argumentumtípusokkal) és példányváltozókat, ellenőrizheti, hogy az osztály megfelelő-e. az adott leszármazottja, és hogy támogatja-e az adott protokollt stb.

A nyelv támogatja a protokollokat (az objektum interfész és a protokoll fogalma egyértelműen elkülönül). Az öröklődés támogatott (nem többszörös); protokollok támogatják a többszörös öröklődést. Egy objektum örökölhető egy másik objektumtól és több protokolltól egyszerre (bár ez inkább nem protokoll öröklődés, hanem annak támogatása).

Az Objective-C-t jelenleg a Clang és a GCC fordítók támogatják ( Windows rendszeren a MinGW vagy a cygwin részeként használják ).

Egyes nyelvi funkciók átkerültek a futásidejű könyvtárba, és nagymértékben függenek tőle. A gcc fordító egy ilyen könyvtár minimális verziójával érkezik. Ingyenesen letöltheti az Apple futásidejű könyvtárát is: az Apple Objective-C futtatókörnyezetét.

Ez a két futásidejű könyvtár hasonló (a fő különbség a metódusnevekben van). A további példák az Apple futásidejű könyvtárára összpontosítanak.

A nyelv szintaxisa

Az Objective-C nyelv speciális típusú azonosítót használ az objektumok kijelölésére (ez hasonló a Java objektumtípusához ). Az id típusú változó valójában egy tetszőleges objektumra mutató mutató. A nulla konstans (= NULL) egy objektumra mutató nullmutatót jelöl.

Ebben az esetben az id helyett használhat egy ismerősebb megnevezést az osztály kifejezett megjelölésével. Ez utóbbi különösen lehetővé teszi a fordító számára, hogy bizonyos objektumokkal ellenőrizze az üzenettámogatást – ha a fordító a változó típusából nem tud arra következtetni, hogy egy objektum támogat egy adott üzenetet, akkor figyelmeztetést ad ki.

Így a nyelv támogatja a típusellenőrzést, de nem szigorú formában (vagyis a talált inkonzisztenciákat figyelmeztetésként ad vissza, nem hibaként).

A következő szintaxist használják az üzenetek küldésére:

[ vevő üzenet ];

Ebben a konstrukcióban a vevő egy objektumra mutató mutató, az üzenet  pedig a metódus neve.

A C++-tól eltérően az üzenet küldése nullára törvényes művelet, mindig nullát ad vissza.

Az üzenet paramétereket is tartalmazhat:

[ myRect setOrigin : 30.0 : 50.0 ];

Ebben a példában a metódus (üzenet) neve setOrigin::. Vegye figyelembe, hogy minden átadott argumentum pontosan egy kettősponttal egyezik meg. Ebben a példában az első argumentumnak van címkéje (a kettőspont előtti szöveg), a másodiknak viszont nincs.

Az Objective-C nyelv lehetővé teszi az egyes argumentumok címkézését, ami nagymértékben javítja a kód olvashatóságát, és csökkenti a rossz paraméter átadásának valószínűségét. A legtöbb fejlesztő ezt a stílust alkalmazza.

[ myRect setWidth : 10.0 magasság : 20.0 ];

Ebben a példában az üzenet neve setWidth: height:.

Támogatja azt is, hogy tetszőleges számú argumentumot adjunk át az üzenetben:

[ myObject makeGroup : obj1 , obj2 , obj3 , obj4 , nil ];

A függvényekhez hasonlóan az üzenetek is visszaadhatnak értékeket, és a C-vel ellentétben az alapértelmezett visszatérési típus az id.

float area = [ myRect area ];

Egy üzenet eredménye azonnal felhasználható egy másik üzenetben:

[ myRect setColor :[ otherRect color ]];

Ahogy korábban említettük, az Objective-C-ben az osztályok maguk is objektumok. Az ilyen objektumok (úgynevezett osztályobjektumok) fő feladata egy adott osztály példányainak létrehozása (gyári metódusminta ) [2] .

Ebben az esetben maga az osztálynév kettős szerepet tölt be - egyrészt adattípusként működik (vagyis az osztály objektumaira mutató mutatók leírására használható). Másrészt az osztálynév működhet objektumként, amelyhez az üzenetet küldik (az üzenetekben az osztálynév csak fogadóként vehet részt).

Rect * myRect = [[ Rect alloc ] init ];

Az Objective-C nem rendelkezik beépített típussal a logikai értékekhez, ezért ezt a típust általában mesterségesen vezetik be. Továbbá a logikai értékekhez a BOOL típust a rendszer a YES és NO lehetséges értékekkel használja (ahogyan a NextStep, Mac OS X operációs rendszereknél is történik).

Az Objective-C nyelv első komolyabb felhasználása a NextStep operációs rendszerben történt. Ehhez a rendszerhez számos különböző Objective-C osztályt írtak, amelyek közül sokat még mindig használnak a Mac OS X rendszerben.

Ezen osztályok nevei az NS előtaggal kezdődnek, jelezve, hogy a NextStep operációs rendszerhez tartoznak. Most bekerültek az Alapítvány könyvtárába, amelyre az OS X és iOS alkalmazások épülnek.

Az egyikkel - az NSStringgel - találkozunk ebben a cikkben. Ez az osztály karakterláncokkal való munkavégzésre szolgál (ebben az esetben a Unicode a karakterek belső reprezentációja).

A fordító támogatja ezt a típust azáltal, hogy a @"my string"-hez hasonló konstrukciókat automatikusan mutatóvá fordítja egy NSString osztály objektumra, amely tartalmazza az adott karakterláncot (pontosabban az állandó karakterláncoknak megfelelő alosztályát).

Tulajdonságok

Tegyük fel, hogy van egy példányváltozónév a Vállalat osztályban.

@interface cég  : NSObject { NString * név ; }

Ha kívülről szeretné elérni, a legjobb, ha az Objective-C 2.0-ban megjelent tulajdonságokat használja. A @property kulcsszó a tulajdonságok deklarálására szolgál.

@ tulajdonság ( megtartása ) NSString * név ;

A zárójelek a példányváltozóhoz tartozó hozzáférési attribútumokat sorolják fel. Az attribútumok 3 fő csoportra oszthatók.

Accessor és mutator nevek

  • A getter=getterName a példányváltozó értékének lekéréséhez használt függvény nevének beállítására szolgál.
  • A setter=setterName a példányváltozó értékének beállításához használt függvény nevének beállítására szolgál.

Olvasási/írási korlát

  • readwrite – a tulajdonságnak van hozzáférője és mutátora is. Az alapértelmezett attribútum.
  • csak olvasható - az ingatlannak csak egy hozzáférője van.

Ezek a tulajdonságok kölcsönösen kizárják egymást. És az utolsó csoport a mutátor attribútumok .

  • hozzárendelés – egy hozzárendelési operátort használunk az új érték beállítására. Csak POD-típusokhoz vagy olyan objektumokhoz használható, amelyek nem a miénk.
  • megtartani - azt jelzi, hogy a példányváltozó új értékeként használt objektum esetében a memóriakezelés manuálisan történik (ne felejtse el később felszabadítani a memóriát).
  • másolás – azt jelzi, hogy az átadott objektum egy másolata kerül felhasználásra a hozzárendeléshez.
  • gyenge analóg az automatikus referenciaszámláló mód használatakor történő hozzárendeléshez . (Az ARC-t a fordítónak támogatnia kell)
  • erős analóg az automatikus referenciaszámláló mód használatakor megtartásra . (Az ARC-t a fordítónak támogatnia kell)

Ha GC alatt dolgozik, nincs különbség a hozzárendelés, megőrzés és másolás között. A tulajdonságok kódjának generálásához, a deklarációban leírt módon, használhatja az automatikus kódgenerálást:

@szintetizáló név ;

Az automatikusan generált kód nem mindig jó megoldás, és előfordulhat, hogy manuálisan kell létrehoznia a példányváltozó-elérőket.

A nyelvet gyakran kritizálják a többi nyelvhez képest túlterhelt szintaxisa miatt. Gyakran megjegyzik azonban jobb olvashatóságát.

Új osztályok létrehozása

Minden Objective-C kulcsszó, amely nem található a C-ben, a @ szimbólummal kezdődik.

A C++-hoz hasonlóan az osztály leírása és megvalósítása el van választva (általában a leírás h kiterjesztésű fejlécfájlokba, a megvalósítások m kiterjesztésű fájlokba kerülnek).

A következő az új osztálydeklaráció általános felépítése:

@interface ClassName  : Szuperosztály { példányváltozódeklarációk _ _ } metódus deklarációk @vége

Az Apple futásidejű verziójában minden osztálynak van egy közös őse, az NSObject osztály, amely számos fontos metódust tartalmaz.

A változók deklarálása nem különbözik a C nyelvben a struktúrákban lévő változók deklarálásától:

Ha nem Apple-t használ, akkor valószínűleg az Object-re (#import <objc/Object.h>) lesz szüksége az NSObject helyett.

@interface Rect  : NSObject { float -width ; úszómagasság ; _ BOOL isFilled ; NSColor * szín ; } @vége

A metódusok leírása markánsan eltér a C++-ban elfogadottaktól, és nagyon hasonlít a Smalltalk nyelvi metódusok leírásaihoz.

Minden leírás plusz vagy mínusz jellel kezdődik. A pluszjel azt jelzi, hogy ez a metódus egy osztálymetódus (azaz csak osztályobjektumoknak küldhető el, ennek az osztálynak a példányaihoz nem). Valójában az osztálymetódusok hasonlóak a C++ nyelv osztályainak statikus metódusaihoz.

A mínusz jel az objektumok metódusainak jelölésére szolgál - ennek az osztálynak a példányai. Ne feledje, hogy az Objective-C-ben minden metódus virtuális , ami azt jelenti, hogy felülbírálhatók.

Az alábbiakban a Rect osztály lehetséges metódusainak leírása található.

@interface Rect  : NSObject { float x , y ; float -width ; úszómagasság ; _ BOOL isFilled ; NSColor * szín ; } + newRect ; - ( üres ) kijelző ; - ( úszó ) szélesség ; - ( úszó ) magasság ; - ( úszó ) terület ; - ( void ) setWidth: ( float ) theWidth ; - ( void ) setHeight: ( float ) theHeight ; - ( void ) setX: ( float ) theX y: ( float ) theY ; @vége

Vegye figyelembe, hogy a metódus neve megegyezhet az osztályba tartozó példányváltozó nevével (például szélesség és magasság).

A metódus visszatérési típusa közvetlenül a plusz vagy mínusz jel után zárójelben van megadva (de a metódus neve előtt). Ha a típus nincs megadva, akkor a rendszer id típusú értéket ad vissza.

Ezután következik a metódus neve, ahol minden kettőspont után megadjuk az argumentum típusát (zárójelben) és magát az argumentumot.

Az Objective-C nyelv lehetővé teszi a következő leírók egyikének megadását is a metódus argumentumokhoz: oneway, in, out, inout, bycopy és byref. Ezek a leírók az adatátvitel irányának és az átvitel módjának meghatározására szolgálnak. Jelenlétük jelentősen leegyszerűsíti a megvalósítást és az elosztott objektumokkal végzett munkát (amelyeket a múlt század 90-es évek elejére implementáltak a NextStep operációs rendszerben).

Egy tetszőleges számú paramétert felvevő módszer a következőképpen írható le:

- makeGroup: ( id ) object , ...;

Ha fejlécfájlt szeretne beilleszteni az Objective-C-be, az #include direktíva helyett az #import direktíva kerül felhasználásra, hasonlóan az #include-hoz, de garantálja, hogy ez a fájl csak egyszer kerül bele.

Egyes esetekben szükségessé válik annak deklarálása, hogy egy adott név egy osztály neve, de anélkül, hogy kifejezetten leírnánk (ilyen igény két osztály leírásakor merül fel, amelyek mindegyike egy másik osztályra vonatkozik).

Ebben az esetben használhatja a @class direktívát, amely deklarálja, hogy az őt követő nevek osztálynevek.

@class Shape , Rect , Oval ;

Az osztálymetódusok megvalósítása így néz ki:

#import "Osztálynév.h" @implementationClassName _ módszer megvalósításai @vége

Az alábbiakban a Rect osztály fentebb ismertetett metódusainak megvalósítási példája látható.

#import "Rect.h" @implementation Rect + újRect { Rect * rect = [[ Rect alloc ] init ]; [ rect setWidth : 1.0f ]; [ rect setHeight : 1.0f ]; [ rect setX : 0.0f y : 0.0f ]; return rect ; } - ( úszó ) szélesség { visszatérési szélesség ; } - ( úszó ) magasság { visszatérési magasság ; } - ( úszó ) terület { return [ self width ] * [ self height ]; } - ( void ) setWidth: ( float ) theWidth { szélesség = theWidth ; } - ( void ) setHeight: ( float ) theHeight { magasság = theHeight ; } - ( void ) setX: ( float ) theX y: ( float ) theY { x = az X ; y = az Y ; } @vége

Amint a fenti példából látható, az összes példányváltozó elérhető a metódusokban. A C++-hoz hasonlóan azonban lehetőség van a változók láthatóságának szabályozására (a metódusok láthatósága nem szabályozható) a @private, @protected és @public direktívákkal (amelyek pontosan úgy működnek, mint a C++ nyelv).

@interfész dolgozó  : NSObject { char * név ; @magán int kor ; char * értékelés ; @védett int job ; lebegő bér ; @nyilvános id főnök }

Ugyanakkor a nyilvános osztályváltozók közvetlenül elérhetők a -> operátor segítségével (például objPtr -> fieldName).

Az üzenetküldési mechanizmus működése

A fordító minden egyes üzenetküldést, azaz az [object msg]-hez hasonló konstrukciót az objc_msgSend függvény hívására fordítja. Ez a függvény első paraméterének egy mutatót vesz fel az üzenet címzett objektumára, második paramétereként pedig az ún. az elküldött üzenet azonosítására szolgáló választó. Ha vannak argumentumok az üzenetben, akkor azok harmadik, negyedik stb. paraméterként is átadódnak az objc_msgSendnek.

Minden Objective-C objektum tartalmaz egy isa attribútumot, amely egy mutató az adott objektum osztályobjektumára. osztály objektumot a fordító automatikusan létrehozza, és egyetlen példányként létezik, amelyre az adott osztály összes példánya hivatkozik az isa-n keresztül.

Minden osztályobjektum szükségszerűen tartalmaz egy mutatót a szülőosztály (szuperosztály) osztályobjektumára és a küldési táblára. Ez utóbbi egy olyan szótár, amely az üzenetválasztókat az azokat megvalósító metódusok (függvények) tényleges címeivel egyezteti.

Így az objc_msgSend függvény az adott objektumhoz keres egy metódust az adott szelektorral a küldési táblában. Ha nincs ott, akkor a keresés folytatódik a feladási táblában a szülőosztálya után, és így tovább.

Ha a metódus (vagyis a hozzá tartozó függvény) megtalálható, akkor az összes szükséges argumentum átvitelével meghívásra kerül.

Ellenkező esetben az objektum egy utolsó esélyt kap az üzenet feldolgozására, mielőtt kivételt dobna - az üzenetválasztó a paraméterekkel együtt egy speciális NInvocation típusú objektumba kerül, és a forwardInvocation: üzenet elküldésre kerül az objektumnak, ahol az NInvocation osztály objektuma paraméterként működik.

Ha egy objektum támogatja a forwardInvocation: funkciót, akkor vagy feldolgozhatja az általa küldött üzenetet, vagy továbbíthatja egy másik objektumnak feldolgozásra:

- ( void ) forwardInvocation: ( NInvocation * ) anInvocation { if ( [ someOtherObject responsesToSelector : [ an Invocation selector ] ] ) [ anInvocation invokeWithTarget : someOtherObject ]; más ........ }

Az üzenetek feladási táblában történő keresésének felgyorsítása érdekében gyorsítótárazást alkalmaznak, ami jelentősen csökkentheti az üzenetküldés költségeit. Ezenkívül megkönnyíti a metódusok táblák közötti keresését az úgynevezett szelektorok használatával a szokásos nevek helyett. A szelektor általában egy 32 bites érték, amely egyedileg azonosít egy metódust.

A kiválasztó típusát SEL-ként jelölik, és számos olyan függvény és konstrukció létezik, amelyek lehetővé teszik egy név szelektorrá alakítását és fordítva.

Tehát az üzenetválasztó közvetlen név szerinti megjelenítéséhez használja a @selector() konstrukciót:

SEL setWidth = @selector ( setWidth :); SEL setPos = @selector ( setPosition : y :);

Az NSSelectorFromString és az NSStringFromSelector függvények arra szolgálnak, hogy egy karakterlánc segítségével jelölőt kapjanak (futás közben), és a szelektort karakterláncsá alakítsák át:

SEL setWidth = NSSelectorFromString ( @"setWidth:" ); NSString * methodName = NSStringFromSelector ( setPos );

Az Objective-C hatékony metainformáció-támogatása lehetővé teszi, hogy futás közben ellenőrizze, hogy egy objektum támogat-e egy metódust egy adott szelektorral azáltal, hogy egy answersToSelector: üzenetet küld neki:

if ( [ anObject responsesToSelector : @selector ( setWidth :) ] ) [ anObject setWidth : 200,0 ];

Elég egyszerű egy adott szelektornak megfelelő üzenetet küldeni (nincs argumentum, egy, két vagy három argumentum) a performSelector:, performSelector: withObject:, performSelector: withObject: withObject:, performSelector: withObject: withObject: withObject: metódussal. , és így tovább.

[ myObject performSelector : sel withObject : nil ];

Vegye figyelembe, hogy a performSelector: metódusok mindig id típusú értéket adnak vissza.

Egy adott objektum osztályát osztályüzenet elküldésével kaphatja meg. Ez az üzenet az osztályt mutatóként adja vissza egy Class típusú objektumra.

Osztály * cls = [ anObject class ]; NSString * clsName = NSStringFromClass ( cls );

Másrészt könnyen megszerezheti a megfelelő osztályobjektumot osztálynév alapján is:

Osztály * cls = NSClassFromString ( clsName );

Valójában mindegyik metódus egy függvény két láthatatlan argumentummal – self és _cmd.

Az első ezzel analóg, vagyis magára az objektumra – az üzenet címzettjére – mutat. A második tartalmazza ennek a módszernek a választóját.

A self argumentum használható üzenetek küldésére önmagának, például a következő módszerrel:

- ( úszó ) terület { return [ self width ] * [ self height ]; }

A self mellett azonban van még egy érték, amelyre üzeneteket lehet küldeni - szuper. Valójában a super nem egy normál változó – ez csak egy újabb jelölés az aktuális objektumra mutató mutatóhoz. De szuperüzenet elküldésekor a metóduskeresés nem az aktuális objektum küldési táblájából indul, hanem a szülőobjektum küldési táblájából.

Így a szupernek küldve az osztály által felülírt metódusok régi verzióit hívjuk meg.

Az Objective-C nyelvben az azt megvalósító függvény címét metódusválasztóval kaphatjuk meg (pontosan úgy, mint egy C nyelvi függvénynél).

Egy ilyen függvény csak abban különbözik a metódus leírásától, hogy két további paramétert szúr be az argumentumlista elejére - egy mutatót magára az objektumra (self) és a metódus választóját (_cmd).

Az objektumnak a methodForSelector: üzenet elküldésével válaszul megkapjuk annak a függvénynek a címét, amely ezt a metódust megvalósítja.

typedef float ( * WidthFunc )( id , SEL ); typedef void ( * SetWidthFunc )( id , SEL , float ); WidthFunc widthFunc = ( WidthFunc ) [ myRect methodForSelector : @selector ( szélesség )]; SetWidthFunc setWidthFunc = ( SetWidthFunc ) [ myRect methodForSelector : @selector ( setWidth :)]; ( * setWidthFunc )( myRect , @selector ( setWidth :), 27.5f );

Ez lehetővé teszi, hogy szükség esetén ismételten meghívjuk ugyanazt a metódust egy adott objektumon, és teljesen elkerüljük az üzenettovábbítással járó költségeket.

Protokollok

Az Objective-C nyelv teljes mértékben támogatja a protokollokat (hasonló a Java interfészével és a C ++ absztrakt osztályával, amelyet néha interfésznek is neveznek). A protokoll egyszerűen a metódusok deklarációinak listája. Egy objektum akkor valósít meg egy protokollt, ha az tartalmazza a protokollban leírt összes metódus megvalósítását.

A protokollok kényelmesek, mivel lehetővé teszik a heterogén objektumok közös jellemzőinek kiemelését és információk átvitelét a korábban ismeretlen osztályok objektumairól.

A protokoll legegyszerűbb leírása a következő:

@protocol ProtocolName metódus deklarációk @vége

Tehát a szerializálható protokoll a következőképpen írható le:

@protokoll Serializable - ( id ) initWithCoder: ( NSCoder * ) kódoló ; - ( void ) encodeWithCoder: ( NSCoder * ) kódoló ; @vége

Egy protokoll tetszőleges számú más protokolltól örökölhető:

@protocol MyProto < Protokoll1 , Protokoll2 , Sorosozható , Rajzolható >

Ugyanígy egy osztály leírásánál nemcsak a szülőosztályt, hanem egy protokollkészletet is megadhat:

@interface MyClass  : SuperClass < Protokoll1 , Protokoll2 , Sorosozható , Rajzolható >

A conformsToProtocol: üzenet használatával futás közben ellenőrizheti, hogy egy objektum támogatja-e az adott objektumprotokollt:

if ( [ myObject conformsToProtocol : @protocol ( Serializable ) ] ) [ myObject encodeWithCoder : myCoder ];

Ezenkívül a protokoll(ok) neve használható változók deklarálásakor, hogy kifejezetten jelezze a fordítónak, hogy a megfelelő objektumok támogatják a protokoll(oka)t.

Tehát, ha a myObject változó tartalmaz egy mutatót egy korábban ismeretlen osztályba tartozó objektumra, de ugyanakkor megfelel a Serializable és Drawable protokolloknak, akkor azt a következőképpen írhatjuk le:

id < Serializálható , Rajzolható > myObject ;

Hasonlóképpen, ha előre ismert, hogy a myObject tartalmazni fog egy mutatót egy olyan objektumra, amely a Shape osztályból örököl, és támogatja a Serializable protokollt, akkor ez a változó a következőképpen deklarálható:

Shape < Serializálható > * myObject ;

Ne feledje, hogy ez a leírás csak arra szolgál, hogy megmondja a fordítónak, hogy az objektum mely üzeneteket támogatja.

Az osztályokhoz hasonlóan az Objective-C minden protokollja objektumokkal van ábrázolva (a Protokoll osztály):

Protokoll * myProto = @protokoll ( Serializálható );

A következő konstrukciót használhatja a protokollok előzetes bejelentéséhez:

@protocol MyProto , Serializálható , Rajzolható ;

Ez a konstrukció közli a fordítóval, hogy a MyProto, Serializable és Drawable olyan protokollnevek, amelyeket később definiálunk.

Kivételkezelés

Az Objective-C támogatja a C++-hoz és a Java-hoz nagyon hasonló kivételkezelést.

Ez a @try, @catch, @finally és @throw utasításokkal történik.

Cup * cup = [[ Cup alloc ] init ]; @próbálja meg { [ csészetöltés ] ; } @catch ( NSException * exc ) { NSLog ( @"Kivétel elkapva:%@" , exc ); } @catch ( azonosító kiv .) { NSLog ( @"Ismeretlen kivétel elkapva" ); } @végül { [ pohárkioldás ] ; }

Kivétel dobásához a @throw direktívát használjuk, argumentumként a kivételobjektumra mutató mutatót használva. A Mac OS X/NextStep általában az NSException osztály objektumait használja erre a célra.

NSException * exc = [ NSException kivételWithName : @ "saját kivétel" oka : @"ismeretlen hiba" userInfo : nil ]; @dobja exc ;

A @catch blokkon belül a @throw direktíva paraméter nélkül használható az újradobás kivételének visszadobására.

Szinkronizálás

Az Objective-C nyelv támogatja a többszálú alkalmazások szinkronizálását. A @synchronized () direktíva használatával megvédheti egy kódrészletet attól, hogy egyszerre több szál egyszerre hajtsa végre .

A @synchronized() bemenetként egy mutatót vesz egy Objective-C nyelvi objektumra (bármilyen objektumot használhat erre a célra, beleértve a self-t is), amely mutex szerepét tölti be .

Amikor egy szál megpróbálja elindítani egy védett töredék végrehajtását, ellenőrzi, hogy a töredéket már végrehajtja-e valamelyik szál. Ha igen, akkor a szálak által a @synchronized()-nek átadott objektumokat a rendszer összehasonlítja.

Ha ezek a mutatók egyeznek, akkor egy védett blokkba belépni próbáló szál felfüggesztésre kerül, amíg az első szál ki nem lép a blokkból. Ezután a második szál végrehajtása folytatódik, és máris „tiltja” ezt a blokkot az összes többi szál számára.

Egy ilyen lehetőség megléte nagyban megkönnyíti az életet többszálú alkalmazások írásakor, amikor nyomon kell követni az azonos adatok egyidejű, több szálon keresztüli megváltoztatására irányuló kísérleteket.

- ( érvénytelen ) kritikus módszer { @szinkronizált ( saját ) { // módosításokat hajt végre a megosztott objektumokon . . . } }

Javasoljuk, hogy egy külsőleg elérhetetlen objektumot mutexként (vagyis a @synchronized utasítás paramétereként) adjunk meg, mivel ez holtponthoz vezethet, ha ugyanazt az objektumot két egymástól függő szál mutexként használja. Különösen a @synchronized(self) elavult.

Objektumok létrehozása és megsemmisítése

Magában az Objective-C nyelvben nincsenek speciális parancsok objektumok létrehozására és megsemmisítésére (például új és törlés). Ez a feladat a futásidejű könyvtárra esik, és az üzenetküldési mechanizmus segítségével valósul meg.

A ténylegesen használt és legszélesebb körben használt séma az Objective-C objektumok létrehozására és megsemmisítésére a NextStep és Mac OS X operációs rendszerekben használt séma, amelyet az alábbiakban ismertetünk.

Egy új objektum létrehozása két lépésből áll: memóriafoglalás és objektum inicializálás. Az első lépést az alloc osztály metódussal valósítjuk meg (az NSObject osztályban implementálva), amely lefoglalja a szükséges memóriamennyiséget (ezt a módszert használják nem csak az NSObject osztály objektumaihoz, hanem bármely onnan örökölt osztályhoz is. ). Ezzel egyidejűleg az isa attribútumhoz egy mutatót írunk a megfelelő osztály osztályobjektumára.

Vegye figyelembe, hogy az alloc üzenetet a rendszer elküldi a kívánt osztály osztályobjektumának, és ez az üzenet egy mutatót ad vissza az objektum lefoglalt memóriájába.

Valójában magának az objektumnak az inicializálását (vagyis példányváltozói értékeinek beállítását, további erőforrások kiosztását stb.) más módszerekkel hajtják végre, a hagyomány szerint ezeknek a módszereknek a neve init-el kezdődik. Általában egy ilyen üzenetet közvetlenül az alloc üzenet után küldenek az üzenet által visszaadott címre.

id anObject = [[ Téglalap alloc ] init ];

A fenti konstrukció a helyes módja egy objektum létrehozásának. Felhívjuk figyelmét, hogy a következő konstrukciók bizonyos esetekben nem működnek:

id anObject = [ Téglalap alloc ]; [ anObject init ];

Ez annak a ténynek köszönhető, hogy számos osztály esetében az init metódus teljesen más mutatót adhat vissza (nem pedig önmagát).

A legegyszerűbb példa arra, hogy mikor fordulhat elő ez a helyzet, a szingutonok (ekkor, ha az osztály egy példánya már létezik, akkor az init metódus felszabadítja az alloc által lefoglalt memóriát, és visszaad egy mutatót a már létrehozott egyetlen példányra) és az objektum gyorsítótárazás, amikor Az objektumok kiosztása a teljesítmény növelése érdekében a blokkokban azonnal megtörténik, és az objektumok nem semmisülnek meg, hanem elmentik újrafelhasználásra.

Új osztály létrehozásakor általában nincs szükség az alloc metódus felülbírálására, de az init metódus felülbírálásának igénye elég gyakran felmerül.

Vegyük észre, hogy az init metódus(ok) csak egy szabályos metódus, semmi különös (ellentétben a C++-val, ahol a konstruktor egy speciális metódus, aminek pl. nem lehet címet adni).

Ezért egy új osztály és init metódus létrehozásakor a felülírt init metódus meghívását ([super init] használatával) kifejezetten a metódus legelején kell végrehajtani.

Az objektumoknak gyakran több metódusuk is van, amelyek init karakterekkel kezdődnek, például init, initWithName:, initWithContentsOfFile: stb.

A bevett gyakorlat ebben az esetben az, hogy az összes inicializálási módszer közül kiemelnek egyet, az úgynevezett kijelölt inicializálót. Minden más init metódusnak meg kell hívnia, és csak ez hívja meg az örökölt init metódust.

- ( id ) initWithName: ( const char * ) theName // kijelölt inicializáló { self = [ szuper init ]; // örökölt metódus meghívása if ( self ) { név = strdup ( theName ); } visszatérő én ; } - ( id ) init { return [ self initWithName : "" ]; }

Bizonyos esetekben kényelmesnek bizonyul a memóriafoglalás és az objektum inicializálása egyetlen (osztály) metódusba kombinálni, például az NSString osztálynak számos osztálymetódusa van, amelyek egy már előkészített (inicializált) objektumot adnak vissza:

+ ( id ) stringCStringgel: ( const char * ) cString kódolás: ( NSStringEncoding ) enc + ( id ) stringWithFormat: ( NSString * ) formátum , ...

A Mac OS X (mint a NextStep) referenciaszámlálást használ az objektumok élettartamának kezelésére – minden objektum tartalmaz egy bizonyos számlálót, amely létrehozáskor egyre van állítva.

Ha megtartási üzenetet küld egy objektumnak, ez eggyel növeli ezt a számlálót (például az összes Foundation library tárolóosztály megtartási üzenetet küld egy objektumnak, ha egy objektumot helyez el bennük).

A bevett gyakorlat az, hogy egy objektumnak minden érdekelt fél (objektum) megtartó üzenetet küld, vagyis ha emlékszik egy tárgyra való hivatkozásra, akkor megtartó üzenetet kell küldenie.

Ha egy objektumra már nincs szükség, a rendszer egyszerűen elküldi a feloldási üzenetet.

Ez az üzenet eggyel csökkenti a számláló értékét, és ha ez egynél kisebb, akkor megsemmisíti az adott objektumot.

Mielőtt egy objektum megsemmisül, dealloc üzenetet küldenek neki, amely lehetővé teszi az objektum inicializálásának végrehajtását. Azonban ez is egy normális üzenet, és ebben kifejezetten meg kell hívnia a legacy implementációt a [super dealloc]-on keresztül a végén.

- ( érvénytelen ) dealloc { . . . [ super dealloc ]; }

Memóriakezelés

Alapelvek

Az Objective-C memóriakezelése az „objektumtulajdonlás” elvén alapul. Az Objective-C memóriakezelésének alapvető szabályai így írhatók fel:

  • Egy objektum tulajdonjogának átvételéhez olyan metódust kell meghívnia, amely a nevében tartalmazza az „alloc”, „new” vagy „copy” kifejezést. Például alloc, newObject, mutableCopy.
  • A fent felsorolt ​​függvényekkel kapott objektum felszabadításához meg kell hívnia a „release” vagy „autorelease” függvényt. Minden más esetben az objektum felszabadítása nem szükséges.
  • Ha az eredményül kapott objektumot meg kívánja őrizni, akkor vagy át kell vennie annak tulajdonjogát (a retain hívásával), vagy másolatot kell készítenie róla (a névben szereplő "copy" elnevezéssel).

Ezek a szabályok az Objective-C elnevezési konvención alapulnak, és egyúttal ennek az egyezménynek az alapját is képezik.

Alapelvek a gyakorlatban

Tegyük fel, hogy van egy osztály Vállalat a programban, amely rendelkezik egy dolgozó módszerrel.

@interface cég  : NSObject { NArray * dolgozók ; } -( NSArray * ) dolgozók ; @vége

Vegyünk egy kis példát egy ilyen osztály használatára:

Vállalat * cég = [[ Company alloc ] init ]; // ... NSArray * dolgozók = [ cég dolgozói ]; // ... [ cégkiadás ] ;

Mivel a Vállalati objektumot kifejezetten létrehozták, meg kell semmisíteni, amikor már nem használják ([vállalati kiadás]). Ugyanakkor a workers metódus neve nem mondja meg, hogy kinek kell törölnie a tömböt. Ilyen helyzetben úgy tekintjük, hogy az alkalmazottak listáját a Vállalat objektum kezeli, és nem szükséges törölni.

Kényelmi kivitelezők

Sok osztály lehetővé teszi egy objektum létrehozásának és inicializálásának kombinálását kényelmi konstruktoroknak nevezett metódusok segítségével; az ilyen metódusokat általában +className-nek nevezik... Feltételezhetjük, hogy a hívó felelős az objektum élettartamának kezeléséért, de ez a viselkedés ellentétes az Objective-C elnevezési konvencióval.

Vállalat * cég = [ Társaság cég ]; [ cégkiadás ] ;

A fenti kódban a [company release] hívás nem engedélyezett , mivel ebben az esetben az objektum élettartamát az autorelease pool segítségével kell kezelni.

A következő példa a vállalati módszer helyes megvalósítására:

+( Társaság * ) cég { id ret = [[ Company alloc ] init ]; return [ ret autorelease ]; } automatikus kiadás

Térjünk vissza a Vállalat osztály dolgozói metódusához. Mivel a return egy tömb, amelynek élettartamát a hívó nem szabályozza, a dolgozók metódusának megvalósítása valahogy így nézne ki:

-( NSArray * ) dolgozói { NNSarray * copy = [[ NNSarray alloc ] initWithArray : dolgozók ] ; return [ copy autorlease ]; }

Az autorelease hívása hozzáadja a másolási objektumot az automatikus kiadási készlethez, így a visszaadott objektum kiadási üzenetet kap, amikor a készletet eltávolítják. Ha egy automatikus kiadási készlethez hozzáadott objektum önmagában kiadási üzenetet küld, akkor hiba történik az automatikus kiadási készlet eltávolításakor.

Objektum visszaadása hivatkozással

Egyes esetekben az objektumok hivatkozással kerülnek visszaadásra, például az NSData osztálymetódus initWithContentsOfURL:options: error: hibaparaméterként (NSError **)errorPtr. Ebben az esetben is működik az elnevezési konvenció, amiből az következik, hogy az objektum tulajdonjogára nincs kifejezett igény, ezért nem szükséges törölni.

Objektumok törlése

Amikor egy objektum referenciaszáma nullára megy, az objektum törlődik. Ebben az esetben a -(void)dealloc metódus kerül meghívásra az objektumon. Ha az objektum bármilyen adatot tartalmaz, azt ebben a függvényben el kell távolítani.

-( void ) dealloc { [ dolgozók felszabadítása ]; [ super dealloc ]; }

Miután a kiadási üzenetet elküldtük az összes osztályváltozónak, meg kell hívni az alaposztály dealloc metódusát. Ez az egyetlen eset, amikor elfogadható a dealloc metódus közvetlen meghívása.

Nincs garancia arra, hogy mikor hívják meg a dealloc metódust. Egyes esetekben előfordulhat, hogy az alkalmazás lejártakor egyáltalán nem hívják meg, hogy időt takarítsunk meg, mivel az operációs rendszer az alkalmazás lejártakor mindenképpen felszabadítja a lefoglalt memóriát. Ennek megfelelően a dealloc módszer nem tartalmazhat olyan módszereket, amelyek felelősek a socketek, fájlok stb. bezárásáért.

Autorlease pool

Az automatikus kiadási készlet azon objektumok tárolására szolgál, amelyekhez a felszabadítási üzenet elküldésre kerül a készlet eltávolításakor. Ahhoz, hogy egy objektumot hozzáadhasson az automatikus kiadási készlethez, egy automatikus kiadási üzenetet kell küldenie.

A Cocoa alkalmazásokban az automatikus kiadási készlet alapértelmezés szerint mindig elérhető. A nem AppKit-alkalmazások esetén magának kell létrehoznia és kezelnie az automatikus kiadási készlet élettartamát.

Az automatikus kiadási készletet az NSAutoreleasePool osztály valósítja meg.

int main ( int argc , const char * argv []) { NSAutoreleasePool * pool = [[ NSAutoreleasePool alloc ] init ] ; Vállalat * cég = [ Társaság cég ]; NArray * dolgozók = [ cég dolgozói ]; [ medence lefolyó ]; return 0 ; }

Az objektumokat az automatikus kiadási készletből nemcsak a felszabadítási üzenet elküldésével, hanem a leürítési üzenet használatával is eltávolíthatja. A kibocsátás és az elvezetés viselkedése referencia-számlálási környezetben azonos. De GC környezetben való futtatás esetén a drain meghívja az objc_collect_if_needed függvényt.

Automatikus kiadási készlet többszálú környezetben

A Cocoa minden szálhoz létrehoz egy saját automatikus kiadási készletet. Amikor a szál véget ér, az automatikus kiadási készlet megsemmisül, és feloldási üzenetet küld a benne lévő összes objektumnak.

A fő szál automatikus kiadási készlete időről időre újra létrejön az alkalmazás által használt memória csökkentése érdekében. Az összes többi szálnál magának kell újra létrehoznia az automatikus kiadási készletet, ami rendkívül fontos a hosszú élettartamú szálak esetében.

Objektumok másolása

Az Objective-C összes objektuma támogathatja a másolást. Egy objektum másolatának létrehozásához meg kell hívnia az NSObject osztályban meghatározott másolási metódust. Másolat létrehozásához az NSCopying protokoll copyWithZone metódusa kerül meghívásra. Az NSObject nem támogatja ezt a protokollt, és ha szükséges, az NSCopying protokollt származtatott osztályokban kell megvalósítani.

A másolatoknak két típusa van: sekély másolat (sekély másolat) és teljes másolat (mély másolat). A különbség ezek között a másolatok között az, hogy sekély másolat készítésekor nem az adatot másoljuk, hanem az adatokat tartalmazó objektumra való hivatkozást. Teljes másolat esetén egy adatot tartalmazó objektum kerül másolásra.

Megvalósítási példa

A másolás megvalósítása eltérő lehet attól függően, hogy a szülőosztály támogatja-e az NSCopying protokollt. Mintakód arra az esetre, amikor a szülő nem valósítja meg az NSCopying protokollt:

@interface Company  : NSObject < NSCopying > { NString * név ; } @ tulajdonság ( megtartása ) NSString * név ; -( id ) copyWithZone: ( NSZone * ) zóna ; @vége @implementation Company @szintetizáló név ; -( id ) copyWithZone: ( NSZone * ) zóna { id copy = [[[ self class ] allocWithZone : zone ] init ]; [ setName másolása :[ saját neve ]]; vissza másolat ; } @vége

Ha a szülő támogatja az NSCopying protokollt, a megvalósítás némileg eltérő lesz: az allocWithZone hívást a copyWithZone váltja fel.

id copy = [ szuper copyWithZone : zóna ]; Megváltozhatatlan objektumok másolása

Módosíthatatlan objektumok esetén nem praktikus másolatot készíteni, és korlátozhatja magát a megtartási üzenet elküldésére.

-( id ) copyWithZone: ( NSZone * ) zóna { return [ selftentart ] ; }

Kategóriák

Az Objective-C nyelv képes új metódusokat hozzáadni a meglévő osztályokhoz. A Ruby , C# , JavaScript és mások nyelvek hasonló képességekkel rendelkeznek . Ehhez nincs szükség osztályforrásokra, és a hozzáadott metódusok automatikusan elérhetővé válnak a változótól örökölt összes osztály számára. Így hozzáadhat egy új metódust az NSObject osztályhoz, és ez a metódus automatikusan hozzáadódik az összes többi osztályhoz.

Azt a mechanizmust, amely lehetővé teszi a meglévő osztályok kiterjesztését (új metódusok hozzáadásával új példányváltozók ilyen módon nem adhatók hozzá), kategóriának nevezzük.

Egy kategóriának saját neve, metóduslistája és az általa kiterjesztett osztály neve van. A kategória leírása így néz ki:

#import "ClassName.h" @interface Osztálynév ( CategoryName ) módszerek deklarációit @vége

A kategória megvalósítása így néz ki:

#import "CategoryName.h" @implementation ClassName ( CategoryName ) módszerek testületek @vége

A kategóriák segítségével olyan tulajdonságokat (tulajdonságokat) hozhat létre, amelyek csak olvashatók lesznek más osztályok számára, és az osztályon belül is olvashatók lesznek:

@interface osztálynév { BOOL zászló ; } @property ( hozzárendelés , csak olvasható ) BOOL flag ; @vége #import "ClassName" @implementation ClassName ( ) // Üres kategória @property ( hozzárendelés , olvasás ) BOOL jelző ; @vége @implementationClassName _ @synthesize flag ; -( void ) someAction { önmaga . flag = IGEN ; } @vége

A kategóriák többek között arra használhatók, hogy egy osztályt valamilyen új protokoll megvalósításával biztosítsanak, például:

@protocol Nyomtatható // nyomtatható entitások -( void ) print ; @vége @interface NSString (Nyomtatható) < Nyomtatható > // az NSString rendszerosztály legyen nyomtatható @end @implementation NSString (Nyomtatható) // új funkció megvalósítása -( void ) print { NSLog ( @"Nyomtatta a %@!" , én ); } @vége

Ezzel szükségtelenné válik egy PrintableString adapterosztály írása az NSString számára.

Osztályobjektumok és az Objective-C futási környezet

Amikor egy programot Objective-C nyelven fordítunk, a fordító minden bevezetett osztályhoz automatikusan létrehoz egy úgynevezett osztályobjektumot - egy teljes értékű objektumot, amely tartalmazza az adott osztályra vonatkozó összes információt, beleértve a nevet, a szuperosztályt, a metódusok listáját és Példányváltozók.

Ráadásul egy ilyen objektum teljes értékű objektum, azaz üzeneteket lehet küldeni neki, paraméterként átadni.

Az osztályobjektumok egyik jellemzője az NSObject osztály összes metódusának támogatása. Azaz üzenet küldésekor az osztálymetódusok között először a szelektort keresik, ha pedig a metódus nem található, akkor az NSObject osztály példány metódusai között folytatódik a keresés.

Egy másik funkció az osztályobjektumok inicializálásának lehetősége – az alkalmazás elején minden osztályobjektum inicializálási (osztály) üzenetet küld.

Ezt az üzenetet garantáltan elküldjük minden osztályobjektumnak, és csak egyszer, mielőtt bármilyen más üzenetet küldenének neki. Az ilyen üzenetek használatának legegyszerűbb példája a Singletons megvalósítása - az inicializálási metódusban kell létrehozni az objektum egyetlen példányát, és el kell tárolni egy statikus változóban.

Az Apple Objective-C futtatókörnyezete nagyszámú C-függvényt tartalmaz, amelyeket az osztályokkal való együttműködésre használnak (közvetlenül futás közben).

A legérdekesebbek a következők:

Method class_getInstanceMethod ( osztály aClass , SEL aSelector ); Method class_getClassMethod ( osztály aClass , SEL aSelector ); struct objc_method_list * class_nextMethodList ( Osztály theClass , void ** iterátor ); void class_addMethods ( Class aClass , struct objc_method_list * methodList ); void class_removeMethods ( Class aClass , struct objc_method_list * methodList ); unsigned method_getNumberOfArguments ( Method metódus ); unsigned method_getSizeOfArguments ( Method metódus ); unsigned method_getArgumentInfo ( Method metódus , int argIndex , const char ** típus , int * offset ); Ivar class_getInstanceVariable ( Class aClass , const char * aVariableName );

A class_getInstanceMethod függvény egy mutatót ad vissza egy olyan szerkezetre (objc_method), amely leírja az adott osztály adott példánymetódusát.

A class_getClassMethod függvény egy mutatót ad vissza egy olyan szerkezetre (objc_method), amely leírja az adott osztály megadott metódusát.

A class_nextMethodList függvény az adott osztály egyik metóduslistáját adja vissza. A következő kódrészlet lehetővé teszi, hogy egy adott osztály összes metódusát átélje.

void * iterátor = 0 ; struct objc_method_list * methodList ; // // A class_nextMethodList minden hívása egy methodList-t ad vissza // methodList = class_nextMethodList ( classObject , & iterator ) while ( methodList != null ) { // ...csináljon valamit az itteni metóduslistával... methodList = class_nextMethodList ( classObject , & iterator ); }

A class_addMethods függvény lehetővé teszi új metódusok hozzáadását egy adott osztályhoz.

A class_removeMethods függvény lehetővé teszi metódusok eltávolítását egy adott osztályból.

method_getNumberOfArguments függvény Az adott metódus argumentumainak számát adja vissza.

A method_getSizeOfArguments függvény az adott metódus összes argumentuma által elfoglalt veremterület méretét adja vissza.

A method_getArgumentInfo függvény információkat ad vissza az adott metódus egyik argumentumáról.

A class_getInstanceVariable függvény információkat ad vissza az osztálypéldányváltozóról, mint mutatót az objc_ivar szerkezetre.

A típusokkal kapcsolatos információk kódolásához speciális karakterlánc-reprezentációt használnak, amely egyértelműen társít egy bizonyos karakterláncot minden adattípushoz. Az @encode () konstrukció segítségével tetszőleges típushoz kifejezetten beszerezhet egy ilyen karakterláncot.

char * buf1 = @encode ( int ** ); char * buf2 = @encode ( struct kulcs ); char * buf3 = @encode ( Téglalap );

Vegyes

Az Apple hivatalos webhelye [3]  a fő információforrás a nyelvről. A fejlesztői fórum, a kódminták és a teljes dokumentáció csak regisztrált fejlesztők számára érhető el.

Az Xcode IDE  az elsődleges Objective-C fejlesztőeszköz. Az IDE csak a Mac OS X operációs rendszert támogatja , és ingyenesen terjeszthető az Apple App Store -on keresztül .

Az Objective-C nyelvről hasznos információk találhatók a hírcsoportban [4] és a levelezőlista archívumában [5] .

A GNUstep [6] projekt a NextStepben és a Mac OS X  -ben használt zárt Foundation és AppKit könyvtárak analógjainak létrehozására tett kísérletet. A könyvtárak forráskódja Objective-C nyelven íródott és szabadon terjeszthető. A projekt webhelyén példák találhatók a nyelv és a forráskód használatára több alkalmazáshoz.

Az Objective-C szinte minden GNU/Linux disztribúción elérhető a gcc projekt által létrehozott gobjc fordítónak köszönhetően .

Az Objective-C használatához Windows operációs rendszer alatt használja a POSIX környezet emulátorokat (ingyenes):

Lásd még

Jegyzetek

  1. https://developer.apple.com/library/mac/documentation/Cocoa/Conceptual/ObjCRuntimeGuide/Articles/ocrtVersionsPlatforms.html
  2. Osztályok meghatározása . Az Objective-C osztályok is objektumok . developer.apple.com _  - "Az osztálymetódus tipikus használata gyári módszer." Letöltve: 2019. december 21. Az eredetiből archiválva : 2020. november 12.
  3. Apple fejlesztő . Letöltve: 2017. szeptember 29. Az eredetiből archiválva : 2011. február 25.
  4. comp.lang.objective-c . Letöltve: 2007. június 14. Az eredetiből archiválva : 2006. november 15..
  5. Objc-nyelv (lefelé irányuló kapcsolat) . Letöltve: 2007. december 17. Az eredetiből archiválva : 2007. december 18.. 
  6. A GNUstep projekt hivatalos weboldala . Letöltve: 2022. május 15. Az eredetiből archiválva : 2021. január 26.

Irodalom

  • Matt Neuburg. iOS 7 programozási alapok: Objective-C, Cocoa és Xcode Basics. - M. : "Williams" , 2014. - 384 p. - ISBN 978-5-8459-1895-6 .
  • Scott Knaster, Waqar Malik, Mark Dalrymple. Tanulja meg az Objective-C-t Mac-en: OS X és iOS rendszerhez, 2. kiadás. - M. : "Williams" , 2013. - 416 p. - ISBN 978-5-8459-1826-0 .
  • Michael Privat, Robert Warner. Alkalmazások fejlesztése Mac OS X Lion rendszerhez. Objective-C programozás Xcode-ban = A Mac OS X Lion Apps fejlesztésének kezdete. — M .: Williams , 2012. — 384 p. - ISBN 978-5-8459-1789-8 .

Linkek

Erőforrások Cikkek