Есть ли возможность конвертировать из UTC время в местное время, используя название страны? [Дубликат]

Когда вы объявляете ссылочную переменную (т. е. объект), вы действительно создаете указатель на объект. Рассмотрим следующий код, в котором вы объявляете переменную примитивного типа int:

int x;
x = 10;

В этом примере переменная x является int, и Java инициализирует ее для 0. Когда вы назначаете его 10 во второй строке, ваше значение 10 записывается в ячейку памяти, на которую указывает x.

Но когда вы пытаетесь объявить ссылочный тип, произойдет что-то другое. Возьмите следующий код:

Integer num;
num = new Integer(10);

Первая строка объявляет переменную с именем num, но она не содержит примитивного значения. Вместо этого он содержит указатель (потому что тип Integer является ссылочным типом). Поскольку вы еще не указали, что указать на Java, он устанавливает значение null, что означает «Я ничего не указываю».

Во второй строке ключевое слово new используется для создания экземпляра (или создания ) объекту типа Integer и переменной указателя num присваивается этот объект. Теперь вы можете ссылаться на объект, используя оператор разыменования . (точка).

Exception, о котором вы просили, возникает, когда вы объявляете переменную, но не создавали объект. Если вы попытаетесь разыменовать num. Перед созданием объекта вы получите NullPointerException. В самых тривиальных случаях компилятор поймает проблему и сообщит вам, что «num не может быть инициализирован», но иногда вы пишете код, который непосредственно не создает объект.

Например, вы можете имеют следующий метод:

public void doSomething(SomeObject obj) {
   //do something to obj
}

В этом случае вы не создаете объект obj, скорее предполагая, что он был создан до вызова метода doSomething. К сожалению, этот метод можно вызвать следующим образом:

doSomething(null);

В этом случае obj имеет значение null. Если метод предназначен для того, чтобы что-то сделать для переданного объекта, целесообразно бросить NullPointerException, потому что это ошибка программиста, и программисту понадобится эта информация для целей отладки.

Альтернативно, там могут быть случаи, когда цель метода заключается не только в том, чтобы работать с переданным в объекте, и поэтому нулевой параметр может быть приемлемым. В этом случае вам нужно будет проверить нулевой параметр и вести себя по-другому. Вы также должны объяснить это в документации. Например, doSomething может быть записано как:

/**
  * @param obj An optional foo for ____. May be null, in which case 
  *  the result will be ____.
  */
public void doSomething(SomeObject obj) {
    if(obj != null) {
       //do something
    } else {
       //do something else
    }
}

Наконец, Как определить исключение & amp; причина использования Трассировки стека

257
задан Richard Everett 6 January 2014 в 09:53
поделиться

11 ответов

Не забывайте, что у вас уже есть объект DateTime и не уверены, что это UTC или Local, достаточно просто использовать методы непосредственно на объекте:

DateTime convertedDate = DateTime.Parse(date);
DateTime localDate = convertedDate.ToLocalTime();

How

Если указанный .net не будет использовать настройки локального компьютера. Я бы прочитал: http://msdn.microsoft.com/en-us/library/system.globalization.daylighttime.aspx

По внешнему виду код может выглядеть примерно так:

DaylightTime daylight = TimeZone.CurrentTimeZone.GetDaylightChanges( year );

И, как уже упоминалось выше, дважды проверьте, в какой временной зоне установлен ваш сервер. В сети есть статьи о том, как безопасно влиять на изменения в IIS.

4
ответ дан Brendan Kowitz 17 August 2018 в 18:32
поделиться
  • 1
    Система будет справляться с этой сложностью для вас, если вы сообщите системе, что такое «вид» вашей даты (local / utc / unspecified). – Drew Noakes 8 June 2009 в 08:47

DateTime по умолчанию имеют Kind of Unspecified, который для целей ToLocalTime считается UTC.

Чтобы получить локальное время Unspecified DateTime, вам просто нужно это сделать:

convertedDate.ToLocalTime();

Невозможно выполнить шаг изменения Kind DateTime с Unspecified на UTC. Unspecified предполагается UTC для целей ToLocalTime: http://msdn.microsoft.com/en-us/library/system.datetime.tolocaltime.aspx

16
ответ дан CJ7 17 August 2018 в 18:32
поделиться
  • 1
    И наоборот: convertedDate.FromLocalTime(); преобразуется в UTC. – R. Schreurs 24 August 2017 в 13:56

Я столкнулся с этим вопросом, так как у меня возникла проблема с датами UTC, когда вы возвращаетесь через API twitter (поле created_at в статусе); Мне нужно преобразовать их в DateTime. Ни один из ответов / примеров кода в ответах на этой странице не был достаточным, чтобы я не смог заставить «String не был признан допустимой ошибкой DateTime» (но это самое близкое, что я нашел, чтобы найти правильный ответ на SO)

Публикует эту ссылку здесь, если это помогает кому-то другому - ответ, который мне нужен, был найден в этом сообщении в блоге: http://www.wduffy.co.uk/blog/parsing-dates-when-aspnets -datetimeparse-doesnt-work / - в основном использовать DateTime.ParseExact со строкой формата вместо DateTime.Parse

1
ответ дан DannykPowell 17 August 2018 в 18:32
поделиться

Я знаю, что это более старый вопрос, но я столкнулся с подобной ситуацией, и мне хотелось поделиться тем, что я нашел для будущих искателей, возможно, включая меня:).

DateTime.Parse() может быть tricky - см. здесь здесь .

Если DateTime поступает из веб-службы или какого-либо другого источника с известным форматом, вы можете рассмотреть что-то вроде

DateTime.ParseExact(dateString, 
                   "MM/dd/yyyy HH:mm:ss", 
                   CultureInfo.InvariantCulture, 
                   DateTimeStyles.AssumeUniversal | DateTimeStyles.AdjustToUniversal)

или, еще лучше,

DateTime.TryParseExact(...)

Флаг AssumeUniversal сообщает парсеру, что дата / время уже UTC; комбинация AssumeUniversal и AdjustToUniversal говорит, что он не должен преобразовывать результат в «локальное» время, которое он попытается сделать по умолчанию. (Я лично стараюсь работать исключительно с UTC на уровне бизнеса / приложения / службы), но в обход преобразования в местное время также ускоряется ситуация - на 50% и более в моих тестах, см. Ниже.)

Вот что мы делали раньше:

DateTime.Parse(dateString, new CultureInfo("en-US"))

Мы профилировали приложение и обнаружили, что DateTime.Parse представляет значительный процент использования ЦП. (Кстати, конструктор CultureInfo был не значительным вкладчиком в использование ЦП.)

Итак, я настроил консольное приложение для синтаксического анализа строки даты / времени 10000 раз в Разнообразие способов. Итог: Parse() 10 секунд ParseExact() (переход на локальный) 20-45 мс ParseExact() (не преобразование в локальный) 10-15 мс ... и да, результаты для Parse() находятся в секунд , тогда как остальные находятся в миллисекундах .

15
ответ дан David 17 August 2018 в 18:32
поделиться
  • 1
    +1 Для профилирования методов анализа. Хорошо знать! – Felix K. 4 April 2014 в 10:34

Для строк, таких как 2012-09-19 01:27:30.000, DateTime.Parse не может определить, в какой часовом поясе указаны дата и время.

DateTime имеет свойство Kind , которое может имеют один из трех параметров часового пояса:

  • Unspecified
  • Локальный
  • Utc

ПРИМЕЧАНИЕ Если вы хотите представить дату / время, отличное от UTC или вашего местного часового пояса, вам следует использовать DateTimeOffset .


Итак, для код в вашем вопросе:

DateTime convertedDate = DateTime.Parse(dateStr);

var kind = convertedDate.Kind; // will equal DateTimeKind.Unspecified

Вы говорите, что знаете, что это такое, так скажите.

DateTime convertedDate = DateTime.SpecifyKind(
    DateTime.Parse(dateStr),
    DateTimeKind.Utc);

var kind = convertedDate.Kind; // will equal DateTimeKind.Utc

Теперь, как только система узнает его в UTC, вы можете просто называть ToLocalTime:

DateTime dt = convertedDate.ToLocalTime();

Это даст вам результат, который вам нужен.

338
ответ дан Drew Noakes 17 August 2018 в 18:32
поделиться
  • 1
    просто еще один способ указать вид: DateTime convertedTime = new DateTime(DateTime.Parse(dateStr).Ticks), DateTimeKind.Utc); – Brad 6 October 2010 в 15:37
  • 2
    это не ToLocalTime ()? @Brad - ваши родители не подходят. – TrueWill 9 February 2011 в 23:50
  • 3
    Учитывает ли это решение переход на летнее время? Когда я пробую это, у меня есть час. – Bob Horn 18 September 2012 в 21:41
  • 4
    Шаг изменения Kind DateTime от Unspecified до UTC не нужен. Unspecified предполагается UTC для целей ToLocalTime: msdn.microsoft.com/en-us/library/… – CJ7 14 November 2012 в 08:43
  • 5
    @ CJ7: Да, но быть явным особенно полезно для других разработчиков, которым, возможно, придется поддерживать код. – Ryan 18 January 2013 в 01:20
TimeZone.CurrentTimeZone.ToLocalTime(date);
43
ответ дан George Johnston 17 August 2018 в 18:32
поделиться
  • 1
    Это работает только в том случае, если система знает, что преобразованная дата находится в UTC. Пожалуйста, см. Мой ответ. – Drew Noakes 8 June 2009 в 08:44
  • 2
    Но UTC - это по умолчанию, не так ли? Следовательно, он работает для "неуказанных" как в ответе CJ7. – NickG 12 June 2013 в 15:06

Я хотел бы добавить общее предупреждение о предостережении.

Если все, что вы делаете, - это получить текущее время от внутренних часов компьютера, чтобы поместить дату / время на дисплей или отчет , тогда все хорошо. Но если вы сохраняете информацию о дате / времени для последующей ссылки или вычисляете дату / время, остерегайтесь!

Предположим, вы определили, что круиз корабль прибыл в Гонолулу 20 декабря 2007 года в 15:00 UTC. И вы хотите знать, что такое местное время. 1. Вероятно, есть, по крайней мере, три «местных». Местный может означать Гонолулу, или это может означать, где находится ваш компьютер, или это может означать местоположение, где находится ваш клиент. 2. Если вы используете встроенные функции для преобразования, это, вероятно, будет ошибкой. Это связано с тем, что переход на летнее время (возможно) на данный момент действует на ваш компьютер, но в декабре не был установлен. Но Windows этого не знает ... все, что у него есть, - это один флаг, чтобы определить, действует ли летнее время. И если он действует, то он с радостью добавит час даже до даты в декабре. 3. Летнее время осуществляется в разных политических подразделениях по-разному (или совсем не). Не думайте, что только потому, что ваша страна меняется в определенную дату, другие страны тоже.

13
ответ дан Mark T 17 August 2018 в 18:32
поделиться
  • 1
    Собственно, № 2 не совсем корректно. На самом деле существуют правила о DST в каждом часовом поясе, которые ваш компьютер будет знать, если информация была установлена ​​(и обновлена). Для многих зон эти правила фиксированы. Другие реализуют «динамический DST». Бразилия - это мое домашнее животное. Таким образом, ваш спутник может работать, если ваше местное время будет DST в декабре, при условии, что между этими моментами никакие изменения не вступают в закон. – Roger Willcocks 16 June 2011 в 13:04
  • 2
    Даже если вы не живете в Бразилии, DST является «динамическим». в том, что политики могут изменить его в любое время (как это было сделано несколько лет назад в США). Поскольку большинство программ написано с учетом будущего использования, важно понять, что нет никакого практического, предсказуемого или даже теоретического способа узнать, какие правила DST будут действовать. Вы можете приблизиться, но сберечь себя от разочарования, отказавшись от совершенства. – DaveWalley 14 May 2014 в 21:45

У меня возникла проблема с тем, что он находился в наборе данных, который проталкивался через провод (webservice к клиенту), который он автоматически изменил бы, потому что поле DateType DataColumn было установлено на локальное. Убедитесь, что вы проверяете, что такое тип DateType, если вы нажимаете DataSets.

Если вы не хотите, чтобы он менялся, установите его в Unspecified

1
ответ дан Miles 17 August 2018 в 18:32
поделиться

Я бы изучил использование класса System.TimeZoneInfo, если вы в .NET 3.5. См. http://msdn.microsoft.com/en-us/library/system.timezoneinfo.aspx . Это должно учитывать изменения дневного света.

// Coordinated Universal Time string from 
// DateTime.Now.ToUniversalTime().ToString("u");
string date = "2009-02-25 16:13:00Z"; 
// Local .NET timeZone.
DateTime localDateTime = DateTime.Parse(date); 
DateTime utcDateTime = localDateTime.ToUniversalTime();

// ID from: 
// "HKEY_LOCAL_MACHINE\Software\Microsoft\Windows NT\CurrentVersion\Time Zone"
// See http://msdn.microsoft.com/en-us/library/system.timezoneinfo.id.aspx
string nzTimeZoneKey = "New Zealand Standard Time";
TimeZoneInfo nzTimeZone = TimeZoneInfo.FindSystemTimeZoneById(nzTimeZoneKey);
DateTime nzDateTime = TimeZoneInfo.ConvertTimeFromUtc(utcDateTime, nzTimeZone);
108
ответ дан Noctis 17 August 2018 в 18:32
поделиться
  • 1
    Если вы работаете в своем часовом поясе (en-NZ в этом случае), вам не нужно иметь дело с TimeZoneInfo. Это просто лишняя сложность. См. Мой ответ для более подробной информации. – Drew Noakes 8 June 2009 в 08:45
  • 2
    +1 за то, что сервер не находится в Новой Зеландии – ajbeaven 7 September 2010 в 08:02
  • 3
    И если кому-то нужно, вот список часовых поясов, которые я нашел для TimeZoneInfo.FindSystemTimeZoneById - codeproject.com/Messages/3867850/… – kape123 25 April 2011 в 20:54
  • 4
    Brilliant! Спасибо за этот пост Dan. Я искал это исправление в течение 3 дней. – Kevin Moore 13 January 2017 в 16:17

В ответ на предложение Даны:

Образец кода теперь выглядит следующим образом:

string date = "Web service date"..ToString("R", ci);
DateTime convertedDate = DateTime.Parse(date);            
DateTime dt = TimeZone.CurrentTimeZone.ToLocalTime(convertedDate);

Исходная дата была 20/08/08; тип был UTC.

Оба «convertDate» и «dt» одинаковы:

21/08/08 10:00:26; вид был локальным

2
ответ дан nzpcmad 17 August 2018 в 18:32
поделиться
  • 1
    Пожалуйста, см. Мой ответ для объяснения этого. – Drew Noakes 8 June 2009 в 08:46
@TimeZoneInfo.ConvertTimeFromUtc(timeUtc, TimeZoneInfo.Local)
1
ответ дан Prince Prasad 17 August 2018 в 18:32
поделиться
Другие вопросы по тегам:

Похожие вопросы: