3

NSDateこの形式に準拠した値を含むオブジェクトはほとんどありませんyyy-MM-dd'T'HH:mm:ss.SSS

フォーマッタなどの別の形式に変換しようとすると、MMM dd, yyyy HH:mm常にnil.

ただし、 object を介して取得した文字列値をハードコーディングするとNSDate、問題なく新しい形式に変換されます。

メソッドを使用してモデルにNSDateオブジェクトを設定しましsetValue:forKey:たが、JSON ライブラリが文字列値を渡す場所に問題があると感じています。ただし、デバッグは、NSDateJSON 経由で返された値が含まれていることを示しています。

この奇妙な動作の原因は何ですか?

これは私の変換コードです:

NSDateFormatter *format = [[NSDateFormatter alloc] init];
[format setDateFormat:@"yyyy-MM-dd'T'HH:mm:ss.SSS"];
NSString *createdDateStr = [format stringFromDate:modelObj.createdDate];
[format setDateFormat:@"MMM dd, yyyy HH:mm"];

NSDate *formattedDate = [format dateFromString:createdDateStr];
NSLog(@"========= REal Date %@",[format stringFromDate:formattedDate]);
4

3 に答える 3

10

編集:あなたの質問を読み直すと、他のことは別として、概念的な誤解があると思います:

次の形式に準拠した値を含む NSDate オブジェクトがほとんどありません

私の知る限り (確かに、私は Objective-C プログラマーではありません)、NSDateオブジェクトはフォーマットについて何も知りません。それはただの瞬間を表しています。テキストから解析されたのか、他の方法で作成されたのかは認識されません。

int変数はint10 進数でも 16 進数でもなく、単なる数値です。それを指定するのは、フォーマットと解析のときです。同様に、 を使用して、解析およびフォーマットの時点でNSDateFormatter必要なフォーマットを記述します。


現在、1 つ NSDateFormatterしかありません。フォーマットを"yyyy-MM-dd'T'HH:mm:ss.SSS"に設定してから、 を呼び出す前にリセットdateFromStringしています。指定したコード スニペットはmodelObj.createdDateISO-8601 形式にフォーマットされますが、「MMM dd, yyyy HH:mm」形式を使用して解析しようとします。

NSDateFormatter2 つの個別のオブジェクトを用意することをお勧めします。

NSDateFormatter *isoFormat = [[NSDateFormatter alloc] init];
[isoFormat setDateFormat:@"yyyy-MM-dd'T'HH:mm:ss.SSS"];
NSString *createdDateStr = [format stringFromDate:modelObj.createdDate];

NSDateFormatter *shortFormat = [[NSDateFormatter alloc] init];
[shortFormat setDateFormat:@"MMM dd, yyyy HH:mm"];

NSDate *parsedDate = [isoFormat dateFromString:createdDateStr];
NSLog(@"========= REal Date %@",[shortFormat stringFromDate:parsedDate]);

formattedDate変数をに変更したことに注意してください。これはparsedDateNSDateテキストを解析して作成されたものです。

コメントに記載されているように、実際にこのようにフォーマットして解析する必要がない限り、そうすべきではありません。元のコードをすべて含めて、日付をフォーマットし、同じ .xml で再解析する方法NSDateFormatterを示しました。次のようにするだけで同じ結果が得られます。

NSDateFormatter *shortFormat = [[NSDateFormatter alloc] init];
[shortFormat setDateFormat:@"MMM dd, yyyy HH:mm"];    
NSLog(@"========= REal Date %@",[shortFormat stringFromDate:modelObj.createdDate]);

一般に、不要な変換は避ける必要があります。テキストからより自然なデータ型に変換NSDate(この場合、数値などにも同じことが当てはまります)、そのデータ型をできるだけ多くのコードに使用し、最後の瞬間にのみテキストに変換します。

于 2012-08-20T07:45:36.063 に答える
4

問題は、ある形式で日付から文字列を作成し、それを別の形式で日付に変換しようとしていることです。文字列から日付を作成するには、その文字列の作成に使用したのと同じ形式を使用する必要があります。そうしないと、nil が返されます。他の形式で書式設定された文字列が必要な場合は、最初に文字列から正しい形式で日付を作成し、それを必要な形式の文字列に変換します。問題は順番です。

NSDateFormatter *format = [[NSDateFormatter alloc] init];
[format setDateFormat:@"yyyy-MM-dd'T'HH:mm:ss.SSS"];
NSString *createdDateStr = [format stringFromDate:modelObj.createdDate];


NSDate *formattedDate = [format dateFromString:createdDateStr];

[format setDateFormat:@"MMM dd, yyyy HH:mm"];
NSLog(@"========= REal Date %@",[format stringFromDate:formattedDate]);

他のアプローチは、混乱を避けるためにJon Skeetが提案するように、さまざまなフォーマッターを使用することです...

于 2012-08-20T07:54:47.263 に答える
1

がありNSDatemodelObj.createdDateそれを特定の形式の文字列としてフォーマットしたいMMM dd, yyyy HH:mm. 日付を文字列に変換してから別の日付に戻し、再度文字列に戻す必要はありませんNSDate。両方の操作に同じフォーマッターを使用すると、開始した日付が同じになるだけです。

最終的な目的の外観に合わせて、日付を一度だけフォーマットする必要があります。

NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
[formatter setDateFormat:@"MMM dd, yyyy HH:mm"];
NSLog(@"========= REal Date %@",[format stringFromDate:modelObj.createdDate]);

NSDate自体は「以下のフォーマットに準拠」していません。形式はありません。基準日からのオフセットである瞬間です。もしそうならNSLog()、それは確かに人間が読める文字列にフォーマットされます(おそらく舞台裏で日付フォーマッタを使用しています)が、それはそれが選択する表現の1つにすぎません。

フォーマッタに渡す文字列の形式は、フォーマッタが期待するものと正確に一致する必要があるため、現在、 nil2 番目の書式設定操作から取得しています。この場合、 format を使用して文字列を作成しましたが、フォーマッタに を期待するように指示したNSDate *formattedDate = [format dateFromString:createdDateStr];ため、そうではありません。したがって、フォーマッタは文字列を解析できず、失敗を示すために戻ります。yyyy-MM-dd'T'HH:mm:ss.SSSMMM dd, yyyy HH:mmnil

于 2012-08-20T07:52:15.030 に答える