Как получить DateTimeOffset с информацией о местном времени - PullRequest
0 голосов
/ 29 мая 2018

У меня есть следующие входные строки:

var timeStr = "03:22";
var dateStr = "2018/01/12";
var format = "yyyy/MM/dd";
var timeZone = "Asia/Tehran";

Это информация о моем времени, timeStr находится в Asia/Tehran часовом поясе и не в UTC.

Используя NodaTime, как я могу получить объект DateTimeOffset с этой информацией, содержащей правильное смещение?

Ответы [ 2 ]

0 голосов
/ 30 мая 2018

Давайте преобразуем всю вашу информацию в соответствующие типы Noda Time:

// Input values (as per the question)
var timeStr = "03:22";
var dateStr = "2018/01/12";
var format = "yyyy/MM/dd";
var timeZone = "Asia/Tehran";

// The patterns we'll use to parse input values
LocalTimePattern timePattern = LocalTimePattern.CreateWithInvariantCulture("HH:mm");
LocalDatePattern datePattern = LocalDatePattern.CreateWithInvariantCulture(format);

// The local parts, parsed with the patterns and then combined.
// Note that this will throw an exception if the values can't be parsed -
// use the ParseResult<T> return from Parse to check for success before
// using Value if you want to avoid throwing.
LocalTime localTime = timePattern.Parse(timeStr).Value;
LocalDate localDate = datePattern.Parse(dateStr).Value;
LocalDateTime localDateTime = localDate + localTime;

// Now get the time zone by ID
DateTimeZone zone = DateTimeZoneProviders.Tzdb[timeZone];

// Work out the zoned date/time being represented by the local date/time. See below for the "leniently" part.
ZonedDateTime zonedDateTime = localDateTime.InZoneLeniently(zone);
// The Noda Time type you want would be OffsetDateTime
OffsetDateTime offsetDateTime = zonedDateTime.ToOffsetDateTime();
// If you really want the BCL type...
DateTimeOffset dateTimeOffset = zonedDateTime.ToDateTimeOffset();

Обратите внимание на «InZoneLeniently», который обрабатывает неоднозначные или пропущенные локальные значения даты / времени, например:

неоднозначные значения отображаются на более раннюю из альтернатив, и «пропущенные» значения сдвигаются вперед на длительность «пробела».

Это может или может быть тем, что вы хотите.Также есть InZoneStrictly, который будет выдавать исключение, если нет единого момента времени, представленного данной локальной датой / временем, или вы можете позвонить InZone и передать свой собственный ZoneLocalMappingResolver.

0 голосов
/ 29 мая 2018

Если вы ищете объект nodatime DateTimeOffset, вы можете сделать следующее:

        var timeStr = "03:22";
        var dateStr = "2018/01/12";
        // DateTime.Parse can deal with this format without specs            
        // var format = "yyyy/MM/dd";
        var timeZone = "Asia/Tehran";


        var date = DateTime.Parse(timeStr + " " + dateStr);
        var zone = DateTimeZoneProviders.Tzdb[timeZone];
        var timespanOffset = zone.GetUtcOffset(SystemClock.Instance.Now).ToTimeSpan();
        var result = new DateTimeOffset(date, timespanOffset);

        Console.Write(result.ToUniversalTime());

Результат: 1/11/2018 10:52:00 PM +00:00, что соответствует времени Тегерана по Гринвичу + 4,5

...