44

NSCalendar で週の最初の曜日を設定する方法があるかどうか、または日曜日ではなく月曜日が週の最初の曜日として既に含まれているカレンダーがあるかどうかは誰にもわかりません。私は現在、1 週間分の作業に基づいたアプリに取り組んでおり、日曜日ではなく月曜日に開始する必要があります。ほとんどの場合、これを回避するために何らかの作業を行うことができますが、多くのまれなケースがあります。プラットフォームが私のためにそれをしてくれることを望みます。

前もって感謝します

ここに私が使用しているコードがあります。今は土曜日なので、平日が 7 ではなく 6 になることを願っています。つまり、日曜日は 0 にロールオーバーするのではなく 7 になります。

NSCalendar *gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
[gregorian setFirstWeekday:0];
unsigned unitFlags = NSYearCalendarUnit | NSMonthCalendarUnit |  NSDayCalendarUnit | NSWeekCalendarUnit | NSWeekdayCalendarUnit;
NSDateComponents *todaysDate = [gregorian components:unitFlags fromDate:[NSDate date]];
int dayOfWeek = todaysDate.weekday;
4

17 に答える 17

78

編集:これは、週の始まりが前月に始まるエッジケースをチェックしません。これをカバーする更新されたコード: https://stackoverflow.com/a/14688780/308315


誰かがまだこれに注意を払っている場合は、使用する必要があります

ordinalityOfUnit:inUnit:forDate:

firstWeekday を 2 に設定します (1 == 日曜日および 7 == 土曜日)。

コードは次のとおりです。

NSCalendar *gregorian = [[[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar] autorelease];
[gregorian setFirstWeekday:2]; // Sunday == 1, Saturday == 7
NSUInteger adjustedWeekdayOrdinal = [gregorian ordinalityOfUnit:NSWeekdayCalendarUnit inUnit:NSWeekCalendarUnit forDate:[NSDate date]];
NSLog(@"Adjusted weekday ordinal: %d", adjustedWeekdayOrdinal);

平日の序数は、ゼロではなく、週の最初の曜日の 1 から始まることに注意してください。

ドキュメント リンク

于 2011-02-11T22:31:34.330 に答える
18

このコードは、現在の週の月曜日に設定された日付を作成します。

NSCalendar *gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];

NSDate *today = [NSDate date];
NSDate *beginningOfWeek = nil;
BOOL ok = [gregorian rangeOfUnit:NSWeekCalendarUnit startDate:&beginningOfWeek
                                interval:NULL forDate: today];
于 2009-12-02T20:16:27.697 に答える
12

setFirstWeekday: NSCalendarオブジェクト。受信者の最初の平日のインデックスを設定します。

- (void)setFirstWeekday:(NSUInteger)weekday

トリックを行う必要があります。

于 2009-07-09T23:29:47.630 に答える
11

私の意見では、この設定はユーザー ロケールに応じて動的にする必要があります。したがって、次を使用する必要があります。

NSCalendar *gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
[gregorian setLocale:[NSLocale currentLocale]];

これにより、カレンダーはユーザー ロケールに従って最初の曜日を自動的に設定します。特定の目的/ユーザー ロケール用にアプリを開発している場合 (または、ユーザーがこの日を選択できるようにしたい場合) を除きます。

于 2010-09-06T06:03:27.460 に答える
8

私はここで多くの答えに苦労しました。. 多分それは私だけでした。.

これが私に役立つ答えです:

- (NSDate*)firstDayOfWeek
{
    NSCalendar* cal = [[NSCalendar currentCalendar] copy];
    [cal setFirstWeekday:2]; //Override locale to make week start on Monday
    NSDate* startOfTheWeek;
    NSTimeInterval interval;
    [cal rangeOfUnit:NSWeekCalendarUnit startDate:&startOfTheWeek interval:&interval forDate:self];
    return startOfTheWeek;
}

- (NSDate*)lastDayOfWeek
{
    NSCalendar* cal = [[NSCalendar currentCalendar] copy];
    [cal setFirstWeekday:2]; //Override locale to make week start on Monday
    NSDate* startOfTheWeek;
    NSTimeInterval interval;
    [cal rangeOfUnit:NSWeekCalendarUnit startDate:&startOfTheWeek interval:&interval forDate:self];
    return [startOfTheWeek dateByAddingTimeInterval:interval - 1];
}

アップデート:

@vikingosegundo によって (他の場所で)指摘されているように、一般的にはローカルに週の開始日を決定させるのが最善ですが、この場合、OP は月曜日に週の開始を要求していたため、コピーしますシステム カレンダーを変更し、firstWeekDay をオーバーライドします。

于 2013-06-23T10:20:36.093 に答える
7

クリスの答えの問題は、週の始まりが前月に始まるエッジケースです。これは簡単なコードで、エッジ ケースもチェックします。

// Finds the date for the first day of the week
- (NSDate *)getFirstDayOfTheWeekFromDate:(NSDate *)givenDate
{
    NSCalendar *calendar = [NSCalendar currentCalendar];

    // Edge case where beginning of week starts in the prior month
    NSDateComponents *edgeCase = [[NSDateComponents alloc] init];
    [edgeCase setMonth:2];
    [edgeCase setDay:1];
    [edgeCase setYear:2013];
    NSDate *edgeCaseDate = [calendar dateFromComponents:edgeCase];

    NSDateComponents *components = [calendar components:NSYearCalendarUnit|NSMonthCalendarUnit|NSWeekCalendarUnit|NSWeekdayCalendarUnit fromDate:edgeCaseDate];
    [components setWeekday:1]; // 1 == Sunday, 7 == Saturday
    [components setWeek:[components week]];

    NSLog(@"Edge case date is %@ and beginning of that week is %@", edgeCaseDate , [calendar dateFromComponents:components]);

    // Find Sunday for the given date
    components = [calendar components:NSYearCalendarUnit|NSMonthCalendarUnit|NSWeekCalendarUnit|NSWeekdayCalendarUnit fromDate:givenDate];
    [components setWeekday:1]; // 1 == Sunday, 7 == Saturday
    [components setWeek:[components week]];

    NSLog(@"Original date is %@ and beginning of week is %@", givenDate , [calendar dateFromComponents:components]);

    return [calendar dateFromComponents:components];
}
于 2013-02-04T14:26:30.267 に答える
3

他のメッセージに誤解が見られます。最初の平日は、0 ではなく 1 です。「Cocoa の日付と時刻のプログラミング ガイドの紹介: 暦計算」にあるように、デフォルトでは Sunday=1 です。

「グレゴリオ暦の日曜日の曜日値は 1 です」

月曜日を最初の就業日として、私が持っている唯一の救済策は、計算を修正するための強引な条件です

NSCalendar *cal=[[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
NSDateComponents *comps = [cal components:NSWeekdayCalendarUnit fromDate:[NSDate date]];
// set to 7 if it's Sunday otherwise decrease weekday number
NSInteger weekday=[comps weekday]==1?7:[comps weekday]-1; 
于 2009-11-11T18:32:58.350 に答える
1

以下では、エッジケースについても説明します。

- (NSDate *)getFirstDayOfTheWeekFromDate:(NSDate *)givenDate
{
    NSCalendar *calendar = [NSCalendar currentCalendar];


   NSDateComponents *components = [calendar components:NSYearCalendarUnit|NSMonthCalendarUnit|NSWeekCalendarUnit|NSWeekdayCalendarUnit fromDate:givenDate];
    [components setWeekday:2]; // 1 == Sunday, 7 == Saturday
    if([[calendar dateFromComponents:components] compare: curDate] == NSOrderedDescending) // if start is later in time than end
    {
        [components setWeek:[components week]-1];
    }

    return [calendar dateFromComponents:components];
}
于 2014-01-19T19:01:28.350 に答える
0

Ivは、nscalenderを使用して平日の名前を表示する方法を見つけました。次のコードを使用します。xcodeメニューバーからコンソールを開いて結果を確認します。コピー次のコードをviewDidLoadメソッドに貼り付けて、週の最初の日を取得します。

NSDate *today = [NSDate date];
NSDateFormatter *dateFormat = [[NSDateFormatter alloc] init];
[dateFormat setDateFormat:@"MM/dd/yyyy :EEEE"];
NSString *dateString = [dateFormat stringFromDate:today];
NSLog(@"date: %@", dateString);
[dateFormat release];
NSCalendar *gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];

NSDateComponents *components = [gregorian components:NSWeekdayCalendarUnit | NSYearCalendarUnit | NSMonthCalendarUnit | NSDayCalendarUnit fromDate:today];
[components setDay:([components day]-([components weekday]-1))];

NSDate *beginningOfWeek = [gregorian dateFromComponents:components];
NSDateFormatter *dateFormat_first = [[NSDateFormatter alloc] init];
[dateFormat_first setDateFormat:@"MM/dd/yyyy :EEEE"];
NSString *dateString_first = [dateFormat_first stringFromDate:beginningOfWeek];
NSLog(@"First_date: %@", dateString_first);

出力は次のようになります。

 date: 02/11/2010 :Thursday
 First_date: 02/07/2010 :Sunday

2010年2月11日にこのプログラムを実行したので、現在の日付に応じて希望の出力が得られます。

同様に、週の最初の営業日、つまり月曜日の日付を取得したい場合は、コードを少し変更するだけです。

変化する :[components setDay:([components day]-([components weekday]-1))];

[components setDay:([components day]-([components weekday]-2))];

その週の月曜日の日付を取得します。

同様に、uは整数-1、-2などを変更することにより、7営業日のいずれかの日付を見つけようとすることができます...

あなたの質問が答えられることを願っています。

ありがとう、ボンソンディアス

于 2010-02-11T07:29:55.990 に答える
0

ISO 8601 カレンダーでは、デフォルトで最初の平日が月曜日に設定されているようです。

于 2014-07-25T13:53:25.383 に答える
-1

…日曜日ではなく月曜日が週の最初の日になっているカレンダーはありますか。

いつか、あるでしょう。

于 2009-10-12T10:22:17.293 に答える
-1

これを行う簡単な方法は、月曜日 = 0、日曜日 = 6 を取得することです。

    NSDateComponents *dateComponents = [[NSCalendar currentCalendar] components:NSWeekdayCalendarUnit fromDate:[NSDate date]];
    NSInteger dayNumStartingFromMonday = ([dateComponents weekday] - 2 + 7) % 7;    //normal: Sunday is 1, Monday is 2
于 2013-09-05T09:26:25.520 に答える