2013-03-06 16 views
13

Ecco il problema, sto cercando un modo per ottenere il numero di settimane in un mese. Ho già trovato una soluzione che sembra funzionare su iOS 5, ma non su IO6 (il numero restituito non è lo stesso, uno in più su iOS 6).Come ottenere il numero di settimane in un mese

- (int)weeksOfMonth:(int)month inYear:(int)year 
{ 
    NSCalendar *cCalendar = [NSCalendar currentCalendar]; 

    NSDateComponents *components = [[NSDateComponents alloc] init]; 
    [components setMonth:month]; 
    [components setYear:year]; 

    NSRange range = [cCalendar rangeOfUnit:NSDayCalendarUnit 
           inUnit:NSMonthCalendarUnit 
           forDate:[cCalendar dateFromComponents:components]]; 

    cCalendar = [NSCalendar currentCalendar]; 
    [cCalendar setMinimumDaysInFirstWeek:4]; 

    NSDateFormatter *dateFormatter = [[NSDateFormatter alloc]init]; 
    [dateFormatter setLocale: [[NSLocale alloc] initWithLocaleIdentifier:@"fr"]]; 
    [dateFormatter setDateFormat:@"yyyy-MM-dd"]; 
    NSMutableSet *weeks = [[NSMutableSet alloc] init ]; 

    for(int i = 0; i < range.length; i++) 
    { 
     NSString *temp = [NSString stringWithFormat:@"%4d-%2d- %2d",year,month,range.location+i]; 
     NSDate *date = [dateFormatter dateFromString:temp ]; 
     int week = [[cCalendar components: NSWeekOfYearCalendarUnit fromDate:date] weekOfYear]; 
     [weeks addObject:[NSNumber numberWithInt:week]]; 
    } 

    return [weeks count]; 
} 

Il valore restituito è 6 su io6 e 5 su io5.

Avete qualche idea?

MODIFICA: Un'altra cosa, il mio dispositivo (ios5) è in francese e il simulatore (ios6) è in inglese. Forse può cambiare qualcosa (come il primo giorno della settimana?)?

+0

Anche in osx dice 6. quale è il conteggio corretto. –

+0

Qual è il mese e l'anno che stai cercando di mostrare il problema? – occulus

+0

Controlla il mio codice di aggiornamento, e lo controllo in osx e ios6, funziona perfettamente. –

risposta

15

Provate questo:

NSDate *date = [NSDate date];//since you are forming date, put it here 
NSCalendar *calender = [NSCalendar currentCalendar]; 
NSRange weekRange = [calender rangeOfUnit:NSWeekCalendarUnit inUnit:NSMonthCalendarUnit forDate:date]; 
NSInteger weeksCount=weekRange.length; 
NSLog(@"%d",weeksCount); 

Swift 4.0:

let date = Date() 
let calendar = Calendar.current 
let weekRange = calendar.range(of: .weekOfMonth, 
           in: .month, 
           for: date) 
let weeksCount = weekRange.count ?? 0 
print(weeksCount) 

O cambiare il metodo di:

- (NSInteger)weeksOfMonth:(int)month inYear:(int)year{ 
    NSString *dateString=[NSString stringWithFormat:@"%4d/%d/1",year,month]; 

    NSDateFormatter *dfMMddyyyy=[NSDateFormatter new]; 
    [dfMMddyyyy setDateFormat:@"yyyy/MM/dd"]; 
    NSDate *date=[dfMMddyyyy dateFromString:dateString]; 

    NSCalendar *calender = [NSCalendar currentCalendar]; 
    NSRange weekRange = [calender rangeOfUnit:NSWeekCalendarUnit inUnit:NSMonthCalendarUnit forDate:date]; 
    NSInteger weeksCount=weekRange.length; 

    return weeksCount; 
} 

EDIT:

uso questo metodo

//NSCalendar *calender = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar]; 
[calender setFirstWeekday:2]; //sunday=1, monday=2 etc 
+0

Grazie per il tuo codice ma il risultato non cambia, ho ancora 5 sul mio dispositivo (ios5) e 6 sul simulatore (ios6). Ho dimenticato una cosa, forse è un problema di localizzazione, forse in francese (come il mio dispositivo è) settimana inizia il lunedì (cosa voglio) ma non in inglese? –

+0

Ecco, questo è il problema, tuttavia hai una soluzione più corta sopra. –

+0

Controlla la mia risposta modificata; –

0

controllare questo approccio di cui sopra.

-(NSArray*)getWeekDaysForDate { 


int dayOfWeek = [self weekDay]; 

NSMutableArray *array = [NSMutableArray array]; 

NSDate *weekStartDate = [self offsetDay:1-dayOfWeek]; 

NSCalendar *calendar = [NSCalendar defaultCalendar]; 
NSInteger monthValue = [self month]; 
unsigned int weekNum = [[calendar components: NSWeekCalendarUnit 
           fromDate: weekStartDate] week]; 
NSDate * nextDate = weekStartDate, *curDate; 
NSDateComponents *oneDay = [[NSDateComponents alloc] init]; 
[oneDay setDay:1]; 
unsigned int newWeekNum; 
do { 
    curDate = nextDate; 
    nextDate = [calendar dateByAddingComponents:oneDay toDate: curDate 
            options:0]; 

    newWeekNum = [[calendar components: NSWeekCalendarUnit fromDate: 
        nextDate] week]; 
    int monthValueForNextDate = [[calendar components: NSMonthCalendarUnit fromDate: 
         nextDate] month]; 

    if(monthValue == monthValueForNextDate) 
     [array addObject:nextDate]]; 

} while (newWeekNum == weekNum); 

[array sortUsingSelector:@selector(compare:)]; 

return array; 
} 

-(int)month { 
    NSCalendar *gregorian = [NSCalendar defaultCalendar]; 
    NSDateComponents *components = [gregorian components:NSMonthCalendarUnit fromDate:self]; 
    return [components month]; 
} 

-(int)weekDay { 
    NSCalendar *gregorian = [NSCalendar defaultCalendar]; 
    NSDateComponents *components = [gregorian components:NSWeekdayCalendarUnit fromDate:self]; 
    return [components weekday]; 
} 

-(NSDate *)offsetDay:(int)numDays { 
    NSCalendar *gregorian = [NSCalendar defaultCalendar]; 
    NSDateComponents *offsetComponents = [[NSDateComponents alloc] init]; 
    [offsetComponents setDay:numDays]; 
    return [gregorian dateByAddingComponents:offsetComponents 
            toDate:self options:0]; 
} 

PS: NSCalendar defaultCalendar = [[NSCalendar alloc]initWithCalendarIdentifier:NSGregorianCalendar];

Aggiungendo questo metodo quindi la categoria di NSDate restituirà i giorni feriali di qualsiasi data che si trova nella stessa settimana.

I migliori saluti.

Problemi correlati