IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

XCode Discussion :

uitableview d'une subview qui crash au chargement [Objective-C]


Sujet :

XCode

  1. #1
    Membre régulier
    Inscrit en
    Mars 2007
    Messages
    120
    Détails du profil
    Informations forums :
    Inscription : Mars 2007
    Messages : 120
    Points : 76
    Points
    76
    Par défaut uitableview d'une subview qui crash au chargement
    Bonjour

    dans mon application j'ai une UIView qui contient un UISearchBar et un UITableview que je charge à partir d'un fichier xml
    tout cela marche parfaitement:

    dans la phase suivante, je dois charger une nouvelle uiview contenant un nouveau uitableview
    lorsque l'utilisateur tappe une chaine dans le searchbar

    j'ai procédé comme suit:

    dans la fonction searchBarSearchButtonclicked
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    	[self.searchBar resignFirstResponder];
    
    	src = [[searchResultController alloc] initWithNibName:@"searchResultController" bundle:nil];
    	[self.navigationController pushViewController:src animated:YES];
    	[self.view addSubview:src.view];
    	[src release];
    J'ai créé un ViewController (searchResultController) et le .xib correspondant (et j'y ai mis le UITableView qui affichera les données).

    J'ai mis le code suivant dans le viewcontoller : (searchResultController.m)
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    - (void)viewDidLoad {	
    	tableauSearch = [[NSMutableArray alloc] init];
    	NSURL *url = [NSURL URLWithString: @"http://www.monsite.com/feed.xml"];
    	XMLToObjectParser *myParser = [[XMLToObjectParser alloc] parseXMLAtURL:url toObject:@"baliseXml" parseError:nil];
    	
    	for(int i = 0; i < [[myParser items] count]; i++) {
    		eventLoc *new = [[eventLoc alloc] init];
    		new = (eventLoc *)[[myParser items] objectAtIndex:i];
    		[tableauSearch addObject:new];
    		[new release];
    	}
    	    [super viewDidLoad];
    }
    /***************************************/
    - (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
        return 1;
    }
    /***************************************/
    - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
    	return [tableauSearch count];
    }
    /***************************************/
    - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
    	static NSString *CellIdentifier = @"Cell";
        UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
        if (cell == nil) {
            cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
        }
    	NSString *ligneTableau = [NSString stringWithFormat:@"%@ %@", [[tableauSearch objectAtIndex:indexPath.row] maBalise1],[[tableauSearch objectAtIndex:indexPath.row] maBalise2]];
    	cell.text=ligneTableau;	// Configure the cell.
        return cell;
    }
    et dans le .h j'ai déclarré un UITableView comme suit :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    IBOutlet UITableView *tblSearchTable;
    ...
    @property (nonatomic, retain) IBOutlet UITableView *tblSearchTable;
    et bien sure dans IB j'ai lié le tblSearchTable avec le UITableView et j'ai connecté datasource et delegete au file's orner
    mais l'application crash au chargement de ce 2eme UITableView.

    (si je déconnecte datasource et delegate du file's owner l'application ne crash pas mais affiche un tableview vide)

    je précise que le 2éme tablview est fait de la même manière que le premier mais ne marche pas :s

    Merci pour votre aide.

  2. #2
    Membre expérimenté Avatar de Ceylo
    Profil pro
    Étudiant
    Inscrit en
    Janvier 2007
    Messages
    1 216
    Détails du profil
    Informations personnelles :
    Âge : 33
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Janvier 2007
    Messages : 1 216
    Points : 1 312
    Points
    1 312
    Par défaut
    Je sais pas du tout si ça va résoudre ton problème, mais j'ai au moins remarqué une boulette.

    Tu écris ceci dans ta méthode -viewDidLoad :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    for(int i = 0; i < [[myParser items] count]; i++) {
        eventLoc *new = [[eventLoc alloc] init];
        new = (eventLoc *)[[myParser items] objectAtIndex:i];
        [tableauSearch addObject:new];
        [new release];
    }
    De une, tu alloues un nouvel objet 'eventLoc', mais tu perds la référence sur cet objet à la ligne suivante. En gros ton allocation n'a servi à rien et n'est jamais libérée => fuite de mémoire.

    De deux (et probablement à cause de la première erreur) : tu appelles -release sur un objet que tu n'as jamais alloué ou sur lequel tu n'as jamais appelé -retain. Donc il ne t'appartient pas et ce n'est pas à toi de gérer sa destruction. Et en faisant un -release, il sera détruit trop tôt. En fait il sera détruit lorsque l'avant dernier objet l'utilisant n'en aura plus besoin. Et le dernier objet l'utilisant va tenter un -release sur un objet déjà détruit => crash.

    En conclusion : tu vires ton alloc et ton release, et ça devrait déjà être mieux .

  3. #3
    Membre régulier
    Inscrit en
    Mars 2007
    Messages
    120
    Détails du profil
    Informations forums :
    Inscription : Mars 2007
    Messages : 120
    Points : 76
    Points
    76
    Par défaut
    Merci d'avoir répondu Ceylo
    le code
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    for(int i = 0; i < [[myParser items] count]; i++) {
        eventLoc *new = [[eventLoc alloc] init];
        new = (eventLoc *)[[myParser items] objectAtIndex:i];
        [tableauSearch addObject:new];
        [new release];
    }
    je l'ai copié d'un tuto.
    je crée un objet de la classe eventLoc, je l'insère dans le tableau et je le détruit.
    et le même code marche sans problème dans la première UIView.

    pour m'assurer j'ai mis une boucle d'affichage à la fin du viewDidLoad:
    et ça affiche le contenu du tableau ac NSLog

    je signale que le crash ne se déclenche que lorsque je lie detegete et datasource au file's owner.

    je compte toujours sur votre aide

  4. #4
    Expert confirmé
    Homme Profil pro
    Inscrit en
    Septembre 2006
    Messages
    2 937
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Septembre 2006
    Messages : 2 937
    Points : 4 358
    Points
    4 358
    Par défaut
    Citation Envoyé par sculpteur Voir le message
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    for(int i = 0; i < [[myParser items] count]; i++) {
        eventLoc *new = [[eventLoc alloc] init];
        new = (eventLoc *)[[myParser items] objectAtIndex:i];
        [tableauSearch addObject:new];
        [new release];
    }
    je l'ai copié d'un tuto.
    mauvais tuto ou mauvaise copie…

    Citation Envoyé par sculpteur Voir le message
    je créé un objet de la classe eventLoc, je l'insère dans le tableau et je le détruit.
    non : entre les 2 vous remplacez la variable par une autre valeur et Ceylo a raison : vous avez un beau memory leak.

    Citation Envoyé par sculpteur Voir le message
    et le même code marche sans problème dans la première UIView.
    parce que vous ne testez pas suffisamment votre code et non pas parce qu'il est correct :
    il vous manque [myParser release] ce qui est un aussi un "memory leak", et si vous aviez "bouché" ce trou-là vous auriez aussi un beau plantage sur la première vue.

    Compilez votre code avec "Build and Analyze" (command-shift-A) au lieu de simplement "Build" et le compilateur vous indiquera toutes les anomalies de ce type.

  5. #5
    Membre régulier
    Inscrit en
    Mars 2007
    Messages
    120
    Détails du profil
    Informations forums :
    Inscription : Mars 2007
    Messages : 120
    Points : 76
    Points
    76
    Par défaut
    il reste un seul memory leak que j'ai pas pu éliminer:
    lorsque j'ajoute: savez vous pourquoi?

    voici mon nouveau code:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     XMLToObjectParser *myParser = [[XMLToObjectParser alloc] parseXMLAtURL:urll toObject "eventLoc" parseError:nil];
    	for(int i = 0; i < [[myParser items] count]; i++) {
    		eventLoc *new = (eventLoc *)[[myParser items] objectAtIndex:i];
    		[tableauSearch addObject:new];
    	}
    	[myParser release];

    (l'application crash toujours) et je ne crois pas que c'est à cause de la gestion de mémoire. j'ai même utilisé un tableau vide pour remplir le tableview mais elle crash comme même. si je relie delegete et datasource au file's owner

  6. #6
    Expert confirmé
    Homme Profil pro
    Inscrit en
    Septembre 2006
    Messages
    2 937
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Septembre 2006
    Messages : 2 937
    Points : 4 358
    Points
    4 358
    Par défaut
    Citation Envoyé par sculpteur Voir le message
    (l'application crash toujours) et je ne crois pas que c'est à cause de la gestion de mémoire. j'ai même utilisé un tableau vide pour remplir le tableview mais elle crash comme même. si je relie delegete et datasource au file's owner
    si l'application se plante quand vous reliez delegate et datasource au file's owner (de quelle classe est-il ?) c'est que forcément il a été "release" quand il ne fallait pas… donc qu'il manque un "retain" dessus…
    et c'est bien un problème de gestion mémoire.

  7. #7
    Membre régulier
    Inscrit en
    Mars 2007
    Messages
    120
    Détails du profil
    Informations forums :
    Inscription : Mars 2007
    Messages : 120
    Points : 76
    Points
    76
    Par défaut
    bon. je suis sure que le problème ne vient pas de la gestions de mémoire car même en utilisant des tableaux vides (sans xml parser ni rien) ça donne la même erreur.

    je vais poser la question autrement:

    comment je peux créer une view qui contient un searchbar controller et un tableview et qu'au clic sur l'un de ses 2 éléments(searchbar ou tableview), je charge une nouvelle view contenant un autre tableview.
    (bien sure en utilisant 2 xib et 2 classes viewcontroller pour ces views)

    Merci encore pour votre écoute les amis.

  8. #8
    Membre régulier
    Inscrit en
    Mars 2007
    Messages
    120
    Détails du profil
    Informations forums :
    Inscription : Mars 2007
    Messages : 120
    Points : 76
    Points
    76
    Par défaut
    est ce que je dois poster ça dans un nouveau topic?

  9. #9
    Membre régulier
    Inscrit en
    Mars 2007
    Messages
    120
    Détails du profil
    Informations forums :
    Inscription : Mars 2007
    Messages : 120
    Points : 76
    Points
    76
    Par défaut
    c'était à cause de la dernière ligne de ce code:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    [self.searchBar resignFirstResponder];
    src = [[searchResultController alloc] initWithNibName:@"searchResultController" bundle:nil];
    [self.navigationController pushViewController:src animated:YES];
    [self.view addSubview:src.view];
    [src release];
    il ne fallait pas éliminer un uiviewcontroller qu'on veut utiliser par la suite

    Merci

  10. #10
    Membre expérimenté Avatar de Ceylo
    Profil pro
    Étudiant
    Inscrit en
    Janvier 2007
    Messages
    1 216
    Détails du profil
    Informations personnelles :
    Âge : 33
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Janvier 2007
    Messages : 1 216
    Points : 1 312
    Points
    1 312
    Par défaut
    L'éliminer oui, mais pas tant que tu en as besoin en effet .

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 4
    Dernier message: 15/08/2010, 14h30
  2. Réponses: 4
    Dernier message: 11/11/2007, 09h41
  3. Réponses: 2
    Dernier message: 26/08/2003, 14h21
  4. Une table qui existe mais qui est inconnu! ?
    Par Nino dans le forum InterBase
    Réponses: 6
    Dernier message: 13/06/2003, 11h47

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo