cocoaheads rennes #9 : gestion mémoire, du débutant à l'expert
DESCRIPTION
La session rennaise des CocoaHeads du mois d'avril 2012 fût l'occasion de revenir sur un des grands sujets d'iOS: la gestion mémoire. Thomas Dupont nous a présenté le sujet en partant des considérations les plus simples en allant vers les cas les plus complexes. Sa présentation est assurément un bon moyen pour se lancer dans le sujet, pour faire un rappel des basiques ou pour aller plus loin ... Une large partie de sa présentation était consacrée à ARC.TRANSCRIPT
![Page 1: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/1.jpg)
Gestion Mémoire
Thomas DupontCocoaHeads Rennes #912 avril 2012
du débutant à l’expert
![Page 2: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/2.jpg)
Sommaire
• Gestion mémoire
• Compteur de références
• Properties
• Blocks
• ARC
![Page 3: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/3.jpg)
•Gestion mémoire
stack
sp
0
1
2
3
4
5
6
7
co if (b) {int y = 3;
}
![Page 4: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/4.jpg)
•Gestion mémoire
stack
sp
0
1
2
3
4
5
6
7
co if (b) {int y = 3;
}
adresse de retour : 4
variable y
![Page 5: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/5.jpg)
heap
•Gestion mémoire
malloc
free
![Page 6: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/6.jpg)
0
Compteur de références
retain
release
NSObject
12
![Page 7: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/7.jpg)
chien
Compteur de références
métaphore du chien
A B
C
0123
‣ Vous êtes responsable des objets que vous créez
‣ Vous pouvez devenir responsable d’un objet avec retain
‣ Vous devez relâcher un objet dont vous êtes responsable
![Page 8: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/8.jpg)
+ (id)alloc- (id)init+ (id)new- (id)copy- (id)mutableCopy
Conventions de nommage
Compteur de références
+ (MyObject*)fetchMyObject;
MyObject* obj = [MyObject fetchMyObject];
![Page 9: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/9.jpg)
obj
Compteur de références
autorelease
autoreleasepoolrun loop
obj01
![Page 10: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/10.jpg)
Properties
assignretain
readonlynonatomicsetter=
@synthesize myObj;
copy
getter=
NSObject* myObj;@property (attributes)
readwrite
![Page 11: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/11.jpg)
Blocks
dispatch_block_t myBlock
[UIView animateWithDuration:0.5 animations:
^{ myView.alpha = 0; }
];
= ;
myBlock
![Page 12: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/12.jpg)
int a = 3;__block
Blocks
void (^incrementA)(void) = ^{ a++; };
incrementA();
![Page 13: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/13.jpg)
Blocks
NSObject* myObj;__block
void (^foo)(void) = ^{ [myObj foo]; };
foo();
![Page 14: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/14.jpg)
Blocks
void (^foo)(void) = ^{myIvar++;[myObj foo];
};foo();
MyObject* myObj;int myIvar;
MyClass.h
MyClass.m
![Page 15: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/15.jpg)
myObj = [[MyObject alloc] initWithBlock:^{NSLog(@"%i",
}];
MyObject* myObj;int myIvar;
myIvar);
MyClass.h
MyClass.m
myObj
blockself
Blocks
![Page 16: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/16.jpg)
myObj = [[MyObject alloc] initWithBlock:^{NSLog(@"%i",
}];
MyObject* myObj;int myIvar;
MyClass* weakSelf = self;
weakSelf-> myIvar);
MyClass.h
MyClass.m__block
myObj
blockself
Blocks
![Page 17: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/17.jpg)
dispatch_block_t block;
if ( ... ) { if ( ... ) {
} else {
}
} else {
}
block();
int* pInt;
int a = 1;pInt = &a;
int b = 1;pInt = &b;
// utilisation de pInt
;^{ ... }block =
Blocks
;^{ ... }block =
![Page 18: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/18.jpg)
dispatch_block_t block;
if ( ... ) {
} else {
}
block();
copy] ;^{ ... }[[ autorelease]block =
Blocks
copy] ;^{ ... }[[ autorelease]block =
![Page 19: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/19.jpg)
ARC
@implementation Stack { NSMutableArray *array; }
@end
- (id) init {if (self = [super init])
array = return self;
}- (void) push: (id) x {
[array addObject: x];}- (id) pop {
id x = [array removeLastObject];return
}
;[[NSMutableArray array]
[array lastObject][ ;
;[
![Page 20: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/20.jpg)
ARC
@implementation Stack { NSMutableArray *array; }
- (void) dealloc { [array release]; [super dealloc]; }@end
- (id) init {if (self = [super init])
array = return self;
}- (void) push: (id) x {
[array addObject: x];}- (id) pop {
id x = [array removeLastObject];return
}
retain] ;[ [NSMutableArray array]
[array lastObject][ retain] ;
autorelease] ;[ x
![Page 21: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/21.jpg)
ARC
It just works !
Oublier la notion de retain et releasePenser au graphe d’objets
Insertion automatique de retain, release et autorelease
![Page 22: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/22.jpg)
__strong objc_retain (
objc_autorelease (
- (id) pop { [array removeLastObject] ;return
}
result =
ARC
__strong
[array lastObject] ;
; result
)
)
valeur par défaut
devient responsable
id
![Page 23: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/23.jpg)
ARC
__unsafe_unretained
ne devient pas responsable
- (void) dealloc {[myTableView setDelegate:nil];[myTableView setDataSource:nil];
}
utilisé pour éviter les deadlocks
![Page 24: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/24.jpg)
ARC
__weak
ne devient pas responsable
utilisé pour éviter les deadlocks
remis à nil dès que l’objet est détruit
! disponible que depuis iOS 5.0 et OS X 10.7
- (void) testWeak {id newObject = [NSObject new];__weak id value = newObject;newObject = nil;assert(value == nil);
}
![Page 25: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/25.jpg)
ARC
@property (strong) id x; // __strong , a.k.a retain
@property (unsafe_unretained) id y; // __unsafe_unretained , a.k.a assign
@property (weak) id z; // __weak
![Page 26: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/26.jpg)
ARC
blocks
![Page 27: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/27.jpg)
^{ ... }
ARC
dispatch_block_t block;
if ( ... ) {
} else {
}
block();
;block =
^{ ... } ;block =
![Page 28: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/28.jpg)
ARC
myObj = [[MyObject alloc] initWithBlock:^{
MyObject* myObj;int myIvar;
MyClass* weakSelf = self;
weakSelf->myIvar);
MyClass.h
MyClass.m__block __unsafe_unretained
}];NSLog(@"%i",
![Page 29: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/29.jpg)
__weak
MyObject* strongSelf = weakSelfif (strongSelf)
ARC
myObj = [[MyObject alloc] initWithBlock:^{
MyObject* myObj;int myIvar;
MyClass* weakSelf = self;
myIvar);
MyClass.h
MyClass.m
}];NSLog(@"%i", strongSelf->
![Page 30: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/30.jpg)
ARC
Core Foundation
![Page 31: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/31.jpg)
CFArrayRef) [[NSArray alloc] init];
NSDictionary*) CFDictionaryCreate(...);
NSString*) myCFString;
ARC
NSDictionary* dict = (
NSString* myNSString = ( __bridge
__bridge_transfer
__bridge_retainedCFArrayRef aray = (
![Page 32: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/32.jpg)
ARC
Project configuration
![Page 33: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/33.jpg)
ARC
![Page 34: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/34.jpg)
ARC
-fno-objc-arc-fobjc-arc
![Page 35: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/35.jpg)
ARC
- (NSString*) copyRightLicense {return license;
}
objc_release ( l );
- (void) checkLicense {NSString* l = [license copyRightLicense];...
}
Non-ARC compiled
ARC compiled
![Page 36: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/36.jpg)
- (void) checkLicense {
...License* l = [License createLicense]
ARC
+ (License*) createLicense {return [[self alloc] init];
}
objc_release ( l );}
Non-ARC compiled
ARC compiled__strong objc_retain ( ;)
![Page 37: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/37.jpg)
ARC
+ (License*) createLicense
- (NSString*) copyRightLicense
NS_RETURNS_RETAINED
NS_RETURNS_NOT_RETAINED ;
;
![Page 39: CocoaHeads Rennes #9 : Gestion mémoire, du débutant à l'expert](https://reader034.vdocuments.net/reader034/viewer/2022051515/55388a105503469f338b481e/html5/thumbnails/39.jpg)
ARCpour ou contre ?