Мы можем использовать класс JSONObject для преобразования строки JSON в объект JSON и итерации по объекту JSON. Используйте следующий код.
JSONObject jObj = new JSONObject(contents.trim());
Iterator<?> keys = jObj.keys();
while( keys.hasNext() ) {
String key = (String)keys.next();
if ( jObj.get(key) instanceof JSONObject ) {
System.out.println(jObj.getString(String key));
}
}
Здесь уже есть некоторые хорошие ответы / комментарии, но просто для прослушивания ...
Есть две причины, по которым я предпочитаю await
по сравнению с Result
(или Wait
). Во-первых, обработка ошибок отличается; await
не завершает исключение в AggregateException
. В идеале, асинхронный код никогда не должен иметь дело с AggregateException
вообще, если только он специально не хочет .
Вторая причина немного более тонкая. Как я описываю в своем блоге (и в книге), Result
/ Wait
может вызвать взаимоблокировки , а может вызвать еще более тонкие взаимоблокировки при использовании в методе async
. Поэтому, когда я читаю код, и вижу Result
или Wait
, это флаг немедленного предупреждения. Result
/ Wait
является правильным, если вы абсолютно уверены , что задача уже завершена. Мало того, что это трудно увидеть с первого взгляда (в коде реального мира), но он также более хрупкий для изменения кода.
Это не значит, что Result
/ Wait
должен никогда . Я следую этим рекомендациям в своем собственном коде:
await
. Result
/ Wait
, если код действительно вызывает его. Result
и Wait
. Обратите внимание, что (1) на сегодняшний день является распространенным явлением, поэтому моя тенденция использовать await
повсюду и рассматривать другие случаи как исключения общего правила.
Это имеет смысл, если timeoutTask
является произведением Task.Delay
, которое я считаю тем, что есть в книге.
Task.WhenAny
возвращает Task<Task>
, где внутренняя задача является одной из тех, которые вы передали в качестве аргументов. Его можно было бы переписать следующим образом:
Task<Task> anyTask = Task.WhenAny(downloadTask, timeoutTask);
await anyTask;
if (anyTask.Result == timeoutTask)
return null;
return downloadTask.Result;
В любом случае, поскольку downloadTask
уже завершен, между return await downloadTask
и return downloadTask.Result
существует очень незначительная разница. Именно в этом будет бросок AggregateException
, который обертывает любое исходное исключение, как указано в комментариях @KirillShlenskiy. Первый будет просто перебрасывать исходное исключение.
В любом случае, где бы вы ни обрабатывали исключения, вы должны в любом случае проверить наличие AggregateException
и его внутренних исключений, чтобы получить причину ошибки.