Получение C # для правильной установки свойства Kind для проанализированной строки ISO 8601 - PullRequest
0 голосов
/ 01 декабря 2018

Я изо всех сил пытаюсь понять, почему при синтаксическом анализе строки в формате ISO 8601 , которая анализируется методом Parse DateTime, неправильно устанавливается свойство Kind нового объекта DateTime.Я рассмотрел пост Как создать .NET DateTime из формата ISO 8601 , и в сочетании с документацией ISO, похоже, что метод Parse должен иметь возможность установить значение Kind, однако этоне.

Пример:

Console.Write(System.DateTime.Parse("2018-11-17T01:00:00").Kind);

Возвраты: не указано

Однако в соответствии со стандартом ISO это действительный формат, который указывает значениеместное время.

Секция часового пояса

Часовые пояса в ISO 8601 представлены как местное время (местоположение не указано), как UTC, или как смещение от UTC.Если информация о соотношении UTC не указана в представлении времени, предполагается, что время указано в местном времени.

Всемирное координированное время (UTC)

Если время указано в UTC, добавьте Z сразу после времени без пробела.Z - это обозначение зоны для нулевого смещения UTC

Еще более странным является то, что добавление Z к строке устанавливает для свойства Kind значение Local.

Чтобы получить Kind значение, правильно установленное для строки UTC, в методе Parse требуется DateTimeStyle of RoundtripKind.Однако, если Z удален из строки, Kind снова устанавливается в Unspecified.

Это проблема с классом DateTime?

Разве Microsoft не следовала стандарту ISO?

Или я не понимаю стандарт ISO?

Ответы [ 3 ]

0 голосов
/ 01 декабря 2018

Не используйте DateTime для разбора строки, но используйте DateTimeOffset.Затем вы можете использовать свойство LocalDateTime или UtcDateTime сгенерированного DateTimeOffset, чтобы явно получить время, представленное строкой, по местному времени или времени UTC.Или вы можете использовать свойство Offset, чтобы проверить, содержит ли строка изначально смещение часового пояса или нет.

0 голосов
/ 02 декабря 2018

Для анализа строки ISO 8601 и установки DateTimeKind можно использовать DateTimeStyles.RoundtripKind с либо стандартным форматом o , либо с пользовательской строкой, включающей спецификатор пользовательского формата K .

Например:

DateTime dt = DateTime.ParseExact(yourISO8601String, "yyyy-MM-dd'T'HH:mm:ss.FFFK",
                                CultureInfo.InvariantCulture, DateTimeStyles.RountripKind);

DateTimeStyles.RoundtripKind обеспечивает следующее поведение:

  • Есливходящее значение не имеет смещения часового пояса, результирующее DateTime будет иметь DateTimeKind.Unspecified
  • Если входящее значение имеет смещение часового пояса Z, результирующее DateTime будет иметь DateTimeKind.Utc
  • Если входящее значение имеет числовое смещение часового пояса, например -07:00, +01:00 или даже +00:00, результирующее DateTime будет иметь DateTimeKind.Local, и значение будет преобразовано изсмещение часового пояса, предоставленное местному часовому поясу.

Хотя это работает во многих случаях, поведение преобразования третьего маркера часто нежелательно, и, следовательно, в большинстве случаев лучше анализироватьDateTimeOffset вместо DateTime.

0 голосов
/ 01 декабря 2018

Вы можете явно указать, что строка должна интерпретироваться как местное время:

Console.Write
(
    DateTime.Parse("2018-11-17T01:00:00", null, DateTimeStyles.AssumeLocal).Kind
);

Вывод:

Local
...