数组问题(Objective C - Google Calendar API);

时间:2012-01-07 03:01:24

标签: objective-c

Day.h

#import <Foundation/Foundation.h>
#import "GData.h"

#define KEY_CALENDAR @"calendar" 
#define KEY_EVENTS @"events"
#define KEY_TICKET @"ticket"
#define KEY_EDITABLE @"editable"

@interface Day : NSObject{
   GDataServiceGoogleCalendar * service;
}

@property (retain) NSDate* date;
@property (retain) NSMutableArray* schedule;
@property (retain) NSMutableArray* allWO;
@property (retain) NSMutableArray* selectedWO;
@property (retain) DistanceMatrixResponse* dmr;
@property (retain) NSMutableArray* array;
@property (retain) NSMutableArray* data;

- (id)init:(NSDate*)d;

@end

Day.m

 @implementation Day

 @synthesize date, schedule, allWO, selectedWO, dmr, array, data;

 - (void)calendarsTicket:(GDataServiceTicket *)ticket finishedWithFeed:(GDataFeedCalendar    *)feed error:(NSError *)error{
  if( !error ){
    int count = [[feed entries] count];
    for( int i=0; i<count; i++ ){
        GDataEntryCalendar *calendar = [[feed entries] objectAtIndex:i];

        // Create a dictionary containing the calendar and the ticket to fetch its events.
        NSMutableDictionary *dictionary = [[NSMutableDictionary alloc] init];
        [data addObject:dictionary];

        [dictionary setObject:calendar forKey:KEY_CALENDAR];
        [dictionary setObject:[[NSMutableArray alloc] init] forKey:KEY_EVENTS];

        if( [calendar ACLLink] )  // We can determine whether the calendar is under user's control by the existence of its edit link.
            [dictionary setObject:KEY_EDITABLE forKey:KEY_EDITABLE];

        NSURL *feedURL = [[calendar alternateLink] URL];
        if( feedURL ){
            GDataQueryCalendar* query = [GDataQueryCalendar calendarQueryWithFeedURL:feedURL];

            NSDate *minDate = [NSDate date];  // Display Event from now
            NSDate *maxDate = [NSDate dateWithTimeIntervalSinceNow:60*60*24*90];  // ...to 90 days from now.

            [query setMinimumStartTime:[GDataDateTime dateTimeWithDate:minDate timeZone:[NSTimeZone systemTimeZone]]];
            [query setMaximumStartTime:[GDataDateTime dateTimeWithDate:maxDate timeZone:[NSTimeZone systemTimeZone]]];
            [query setOrderBy:@"starttime"];
            [query setIsAscendingOrder:YES];
            [query setShouldExpandRecurrentEvents:YES];

            GDataServiceTicket *ticket = [service fetchFeedWithQuery:query
                                                            delegate:self
                                                   didFinishSelector:@selector(    eventsTicket:finishedWithEntries:error: )];
            [dictionary setObject:ticket forKey:KEY_TICKET];
        }

    }
}else
    NSLog(@"Some Error: 1");

NSLog(@"POINT 1-=-=-=-=-=-=-=-= %d", [data count]);
array = [[NSMutableArray alloc] initWithArray:data copyItems:YES];


 }

- (void)eventsTicket:(GDataServiceTicket *)ticket finishedWithEntries:(GDataFeedCalendarEvent *)feed error:(NSError *)error{
if( !error ){
    NSMutableDictionary *dictionary;
    for( int section=0; section<[data count]; section++ ){
        NSMutableDictionary *nextDictionary = [data objectAtIndex:section];
        GDataServiceTicket *nextTicket = [nextDictionary objectForKey:KEY_TICKET];
        if( nextTicket==ticket ){       // We've found the calendar these events are meant for...
            dictionary = nextDictionary;
            break;
        }
    }

    if( !dictionary )
        return;     // This should never happen.  It means we couldn't find the ticket it relates to.

    int count = [[feed entries] count];

    NSMutableArray *events = [dictionary objectForKey:KEY_EVENTS];

    for( int i=0; i<count; i++ ){
        [events addObject:[[feed entries] objectAtIndex:i]];
    }


    NSURL *nextURL = [[feed nextLink] URL];
    if( nextURL ){    // There are more events in the calendar...  Fetch again.
        GDataServiceTicket *newTicket = [service fetchFeedWithURL:nextURL
                                                         delegate:self
                                                didFinishSelector:@selector( eventsTicket:finishedWithEntries:error: )];   // Right back here...
        // Update the ticket in the dictionary for the next batch.
        [dictionary setObject:newTicket forKey:KEY_TICKET];
    }
}else
    NSLog(@"Some error: 2");
//[self handleError:error];

}

- (void)refresh{

[data removeAllObjects];


GDataServiceTicket *ticket =[service fetchCalendarFeedForUsername:googleusername
                             delegate:self
                    didFinishSelector:@selector( calendarsTicket:finishedWithFeed:error:   )];


}



- (id)init:(NSDate*)d
{

self = [super init];
if(self){

    NSArray* days = [[NSArray alloc]initWithObjects:@"Sunday", @"Monday", @"Tuesday", @"Wednesday", @"Thursday", @"Friday",@"Saturday", nil];
    data = [[NSMutableArray alloc]init];
    self.date = d;
    self.allWO = [[NSMutableArray alloc]init];
    self.selectedWO = [[NSMutableArray alloc]init];
    self.schedule = [[NSMutableArray alloc]init];
    NSCalendar *gregorian = [[NSCalendar alloc]
                             initWithCalendarIdentifier:NSGregorianCalendar];
    NSDateComponents *weekdayComponents = [gregorian components:(NSDayCalendarUnit | NSWeekdayCalendarUnit) fromDate:self.date];
    NSInteger dayofweek = [weekdayComponents weekday];
    int st = 600;
    for(int i = 0; i<32; i++){
        int et = st +50;
        TimePeriod* tp = [[TimePeriod alloc]init:[days objectAtIndex:dayofweek-1]: st%100 == 0?st:st-20  :et%100 == 0?et:et-20];
        [schedule addObject:tp];
        st+=50;
    }

    service = [[GDataServiceGoogleCalendar alloc] init];

    [service setUserCredentialsWithUsername:googleusername
                                   password:googlepassword;

    [self refresh];
    NSLog(@"Count: %d", [array count]);


  }
  return self;
 }
}

@end

只是想知道是否有人可以提供帮助!

上述代码旨在检索所有用户googleCalendar事件和日历,并将其存储在&#34;数据&#34; NSMutableArray里。它完美地做到了。我使用的Google用户有三个日历,因此此行的计数

     NSLog(@"POINT 1-=-=-=-=-=-=-=-= %d", [data count]);

打印3,应该如此。但是在这一行,计数仍为0。

NSLog(@"Count: %d", [array count]); 

我相信当调用[self refresh]时代码会继续运行

[service fetchCalendarFeedForUsername:googleusername
                             delegate:self
                    didFinishSelector:@selector( calendarsTicket:finishedWithFeed:error:   )];

已经跑完了。

我只需要在日期对象中保留一系列Days事件(来自Google日历)。

有什么建议吗?

2 个答案:

答案 0 :(得分:1)

让我用这种方式解释一下:

声明了MyClass并包含一个名为“theArray”的实例变量。

MyClass* instanceA = [[MyClass alloc] init]; // init leaves "theArray" nil
MyClass* instanceB = [[MyClass alloc] init];
[instanceA someMethodThatSetsTheArray];
[instanceB someMethodThatReferencesTheArray];

第二个方法调用将发现“theArray”为零。

答案 1 :(得分:0)

你在问题​​中的想法是正确的:

  

我相信当调用[self refresh]时代码会继续运行

     

[service fetchCalendarFeedForUsername:...

     

已经跑完了。

这是完全正确的。在异步服务调用返回数据之前,您没有设置array,这是在您的init方法返回之后的。所以你只是过早地阅读array

事实上,您会在日志中注意到这一行:

NSLog(@"Count: %d", [array count]);

打印 之前:

NSLog(@"POINT 1-=-=-=-=-=-=-=-= %d", [data count]);