TableView Crasht beim scrollen

Diese Seite verwendet Cookies. Durch die Nutzung unserer Seite erklären Sie sich damit einverstanden, dass wir Cookies setzen. Weitere Informationen

  • TableView Crasht beim scrollen

    Mein Tableview Controller crasht jedes mal wenn ich anfange zu scrollen. Es gibt hier schon ein paar Themen dazu aber keines hat mir weitergeholfen.
    Ich bin noch neu in der Iphone programmierung und würde mich sehr freuen wenn mir hier jemand helfen könnte.

    Der error code mit nszombies ist:

    Quellcode

    1. [StateTableViewController respondsToSelector:]: message sent to deallocated instance 0x59757c0



    ohne nszombies gibts gar keine meldung und es crasht einfach.


    hier der code:


    Quellcode

    1. #import "StateTableViewController.h"
    2. @implementation StateTableViewController
    3. #pragma mark -
    4. #pragma mark init
    5. - (id)init {
    6. [super initWithNibName:nil bundle:nil];
    7. UITabBarItem *tbi = [self tabBarItem];
    8. [tbi setTitle:@"Bundesländer"];
    9. states = [[NSMutableArray alloc] init];
    10. //Database
    11. NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    12. NSString *path = [paths objectAtIndex:0];
    13. NSString *fullPath = [path stringByAppendingPathComponent:@"kulturfahrt.db"];
    14. NSFileManager *fm = [NSFileManager defaultManager];
    15. BOOL exists = [fm fileExistsAtPath:fullPath];
    16. if (exists) {
    17. NSLog(@"%@ exists - just opening", fullPath);
    18. } else {
    19. NSLog(@"%@ does not exist - copying and opening", fullPath);
    20. NSString *pathForStartingDB = [[NSBundle mainBundle] pathForResource:@"kulturfahrt" ofType:@"db"];
    21. BOOL success = [fm copyItemAtPath:pathForStartingDB toPath:fullPath error:NULL];
    22. if (!success) {
    23. NSLog(@"database copy failed");
    24. }
    25. }
    26. const char *cFullPath = [fullPath cStringUsingEncoding:NSUTF8StringEncoding];
    27. if (sqlite3_open(cFullPath, &database) != SQLITE_OK) {
    28. NSLog(@"unable to open database at %@", fullPath);
    29. }
    30. //Database query
    31. if (!statement) {
    32. char *cQuery = "SELECT id, name FROM STATES ORDER BY id";
    33. if (sqlite3_prepare_v2(database, cQuery, -1, &statement, NULL) != SQLITE_OK) {
    34. NSLog(@"query error : %s", statement);
    35. }
    36. }
    37. while (sqlite3_step(statement) == SQLITE_ROW) {
    38. const char *cStateName = (const char *)sqlite3_column_text(statement, 1);
    39. NSString *stateName = [[[NSString alloc] initWithUTF8String:cStateName] autorelease];
    40. NSInteger iStateId = sqlite3_column_int(statement, 0);
    41. NSNumber *nStateId = [NSNumber numberWithInt:iStateId];
    42. NSDictionary *stateDict = [[NSDictionary alloc] initWithObjectsAndKeys:nStateId,@"id",
    43. stateName,@"name", nil];
    44. //NSLog(@"%@, %@", nStateId, stateName);
    45. [states addObject:stateDict];
    46. [stateDict release];
    47. }
    48. sqlite3_reset(statement);
    49. return self;
    50. }
    51. #pragma mark -
    52. #pragma mark lifecycle
    53. - (void)dealloc {
    54. [states release];
    55. states = nil;
    56. sqlite3_close(database);
    57. [super dealloc];
    58. }
    59. #pragma mark -
    60. #pragma mark Table View Data Source Methods
    61. - (NSInteger)tableView:(UITableView *)table numberOfRowsInSection:(NSInteger)section {
    62. return [states count];
    63. }
    64. - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)ip {
    65. NSDictionary *stateDict = [states objectAtIndex:[ip row]];
    66. NSString *name = [stateDict objectForKey:@"name"];
    67. UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"UITableViewCell"];
    68. if (!cell) {
    69. cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault
    70. reuseIdentifier:@"UITableViewCell"];
    71. [cell autorelease];
    72. }
    73. [[cell textLabel] setText:name];
    74. return cell;
    75. }
    76. @end
    Alles anzeigen

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von ZeRo ()

  • Das kann alles sein. Angefangen von der Nachricht "message" (kluge Namensgebung übrigens, man weiss sofort worum es geht!) über fehlende getter/setter ("states" scheint eine Instanzvariable zu sein.) bis zum nicht dargestellten "loadView" (Machst Du es überhaupt?) scheinen da einige Problemkreise vorgezeichnet.
    I would be embarrassed if they did not spy on me.
  • longW schrieb:

    Das kann alles sein. Angefangen von der Nachricht "message" (kluge Namensgebung übrigens, man weiss sofort worum es geht!) über fehlende getter/setter ("states" scheint eine Instanzvariable zu sein.) bis zum nicht dargestellten "loadView" (Machst Du es überhaupt?) scheinen da einige Problemkreise vorgezeichnet.
    states ist mein array für meine daten, da greife ich ja nicht von außerhalb darauf zu, also brauch ja keine getter und setter dafür oder? Außerdem funktioniert es ja bis ich anfange zu scrollen. "states" haben eine länge von 16. Ich kann mit nslog auf alle zugreifen. Irgendwann wird aber entweder meine daten in meinem Array "states" oder das Array selber anscheinend deallocated. Ich weiß nur nicht wo, und ich weiß auch nicht obs vielleicht an was anderem liegt.
    loadView hab ich natürlich drinnen, ich hab dort nur noch nichts implementiert, also hab ichs rausgelassen.

    Und keine ahnung zu dem "message". Das hat mir der debugger so rausgespuckt.
  • Du solltest mal einen Blick in den Debugger werfen. Der zeigt Dir an, wo Deine App abstürzt.

    Die Initialisierung der Daten gehört nicht in den Initializier sondern in viewDidLoad oder viewDidAppear: . Der Zugriff auf den TabBarItem sollte auch nicht funktionieren, weil der Controller im Initializer noch keinen View hat. Da Du die Daten komplett fetchst, solltest Du die Verbindung auch direkt schließen und nicht erst im dealloc.
    „Meine Komplikation hatte eine Komplikation.“
  • Der Debugger wechselt dann zum Maschinencode, ich kann also nicht genau sagen wo es abstürzt, oder benutze ich den Debugger falsch?

    Ich hab jetzt alles aus der init() in die viewDidLoad gehauen, aber kein unterschied. Es crasht immer noch zur genau der selben Zeit direkt dann wenn ich nach unten scrolle.

    Ich dachte der fehler wäre in der

    Quellcode

    1. - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)ip {}
    methode. Da ich annahm dass ich hier auf eine deallocierte Variable zugreife. Wenn ich jedoch alle variablen zugriffe rauskommentiere und dann versuche zu scrollen passiert das gleiche.

    Kann es sein, dass ich diesen Fehler bekommen kann weil ich einen UITabBar mit einer UINavigationBar und einem TableView kombiniere?
    Meine Struktur ist: NavigationBar enthält TabBar, TabBar enthält TableView.

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von ZeRo ()

  • ZeRo schrieb:

    Der Debugger wechselt dann zum Maschinencode, ich kann also nicht genau sagen wo es abstürzt, oder benutze ich den Debugger falsch?

    Die Absturzstelle liegt meistens in den Cocoa-Tiefen. Im Debugger kannst Du Dir auf der linken Seite aber den Stack ansehen. Da siehst Du meistens, wer den Fehler verursacht hat.

    ZeRo schrieb:

    Ich hab jetzt alles aus der init() in die viewDidLoad gehauen, aber kein unterschied. Es crasht immer noch zur genau der selben Zeit direkt dann wenn ich nach unten scrolle.

    Der entscheidende Unterschied ist, dass in der genannten Methode der View des ViewControllers bereits geladen wurde und Du auf dessen UI-Elemente zugreifen kannst.

    Dein Speicherverwaltungsfehler scheint aber auch nicht in Deinem TableViewController zu liegen. Wie legst Du den an und wie gibst Du den wieder frei?
    „Meine Komplikation hatte eine Komplikation.“
  • Das steht beim Absturz links drinnen, da werd ich leider nicht schlau draus.

    Quellcode

    1. #0 0x0237ce07 in ___forwarding___#1 0x0237ccd2 in __forwarding_prep_0___#2 0x002fbcdd in -[UIScrollView _updatePanWithStartDelta:event:gesture:ignoringDirectionalScroll:]#3 0x00305b19 in -[UIScrollView handlePan:]#4 0x0052b394 in -[UIGestureRecognizer _updateGestureWithEvent:]#5 0x00527bf3 in -[UIGestureRecognizer _delayedUpdateGesture]#6 0x0052c486 in _UIGestureRecognizerUpdateObserver#7 0x0052d798 in _UIGestureRecognizerUpdateGesturesFromSendEvent#8 0x002dbbcd in -[UIWindow _sendGesturesForEvent:]#9 0x002d713a in -[UIWindow sendEvent:]#10 0x002bb1ec in -[UIApplication sendEvent:]#11 0x002bfac4 in _UIApplicationHandleEvent#12 0x02bf7afa in PurpleEventCallback#13 0x023ecdc4 in __CFRUNLOOP_IS_CALLING_OUT_TO_A_SOURCE1_PERFORM_FUNCTION__#14 0x0234d737 in __CFRunLoopDoSource1#15 0x0234a9c3 in __CFRunLoopRun#16 0x0234a280 in CFRunLoopRunSpecific#17 0x0234a1a1 in CFRunLoopRunInMode#18 0x02bf62c8 in GSEventRunModal#19 0x02bf638d in GSEventRun#20 0x002c3b58 in UIApplicationMain#21 0x00001d44 in main at main.m:14



    So lege ich meine TableView an:

    Quellcode

    1. #import "MySignsTabBarController.h"
    2. #import "StateTableViewController.h"
    3. #import "HighwayTableViewController.h"
    4. @implementation MySignsTabBarController
    5. // Implement viewDidLoad to do additional setup after loading the view, typically from a nib.
    6. - (void)viewDidLoad {
    7. [super viewDidLoad];
    8. tabBarController = [[UITabBarController alloc] init];
    9. UIViewController *vc1 = [[StateTableViewController alloc] init];
    10. UIViewController *vc2 = [[HighwayTableViewController alloc] init];
    11. NSArray *viewControllers = [NSArray arrayWithObjects:vc1, vc2, nil];
    12. [vc1 release];
    13. [vc2 release];
    14. [tabBarController setViewControllers:viewControllers];
    15. [self setView:[tabBarController view]];
    16. [[self navigationItem] setTitle:@"Schilder"];
    17. }
    18. - (void)didReceiveMemoryWarning {
    19. // Releases the view if it doesn't have a superview.
    20. [super didReceiveMemoryWarning];
    21. // Release any cached data, images, etc that aren't in use.
    22. }
    23. - (void)viewDidUnload {
    24. [super viewDidUnload];
    25. [tabBarController release];
    26. tabBarController = nil;
    27. // Release any retained subviews of the main view.
    28. // e.g. self.myOutlet = nil;
    29. }
    30. - (void)dealloc {
    31. [tabBarController release];
    32. [super dealloc];
    33. }
    34. @end
    Alles anzeigen
  • ZeRo schrieb:

    Wie bekomme ich denn sonst die Views auf den Screen?

    statt

    Quellcode

    1. [window addSubview:tabBarController.view];


    habe ich

    Quellcode

    1. [self setView:[tabBarController view]];

    gemacht. Ansonsten is ja der Code gleich.


    Genau deswegen sollte man sich um die Grundlagen kümmern.
    Was ist 'window', wo kommt es her, und was machs es auf dem iPhone.
    I would be embarrassed if they did not spy on me.
  • Der code davor ist gleich. Wie dem TabBarController die anderen Controller geaddet wurden.

    Mir ist klar dass diese beiden zeilen nicht gleich sind. Wie kann ich also die View setzen? Jedes beispiel dort zeigt es nur mit dem 'window' auf das ich ja jetzt keinen zugriff habe oder?

    @longW: Deine Antwort war nicht sehr hilfreich...

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von ZeRo ()

  • Schau Dir doch mal die App an, die aus dem Template Tab Bar Application in Xcode erzeugt wird. Da bekommst Du schon eine Vorstellung, wie es laufen sollte. Allerdings wirst Du um das Lesen von Grundlagen nicht herum kommen.

    Die Zeit, die Du in die Einarbeitung steckst, bekommst Du später um ein Vielfaches zurück. Beispielsweise ist das Ableiten des UITabBarControllers nur in seltenen Fällen wirklich notwendig.
    „Meine Komplikation hatte eine Komplikation.“