c# - это в порядке для встраивания “попытки/выгоды” в операторе “использования” для веб-запроса? Мой код является правильным?

Это в порядке для встраивания "попытки/выгоды" в операторе "использования" для веб-запроса? Мой код является правильным? Это - мои требования:

  1. Хочу использовать оператор "использования", чтобы удостовериться, что средства высвобождены в любом случае на HttpWebResponse

    • Но все еще хочу сделать некоторый пользовательский материал, если существует ре исключения HttpWebResponse и "ответ = (HttpWebResponse) запрос. GetResponse ()";в частности.

Мой исходный код:

        var result = new HttpHeaderInfo();
        HttpWebRequest request = null;
        HttpWebResponse response = null;
        using (response)
        {
            try
            {
                request = (HttpWebRequest)WebRequest.Create(uri);
                request.Method = "HEAD";
                request.KeepAlive = false;
                request.Timeout = Properties.Settings.Default.WebTimeoutDefault;

                response = (HttpWebResponse)request.GetResponse();
                result.LastModified = response.LastModified;
                result.ContentType = response.ContentType;
                result.StatusCode = response.StatusCode;
                result.ContentLength = response.ContentLength;
            }
            catch (Exception ex)
            {
                if (ex is InvalidOperationException ||
                    ex is ProtocolViolationException ||
                    ex is WebException)
                {
                    result.HttpError = ex;
                    result.LastModified = System.DateTime.MinValue;
                    result.ContentType = null;
                }
                else { throw; }
            }

        }

спасибо

6
задан Greg 1 February 2010 в 06:45
поделиться

3 ответа

Это нормально, но немного избыточно; в общем смысле, вы можете легко удалить с помощью блока , добавить блок finally после catch и явно вызвать Dispose в там, что уменьшит вложенность в ваш код.

В более конкретном смысле меня немного беспокоит то, что вы фактически не назначаете ответ , пока не получите внутри с использованием блока , и явные объявления переменных не нужны и сбивают с толку в этом контексте. Я бы переписал его так:

HttpHeaderInfo result;
try
{
    var request = (HttpWebRequest)WebRequest.Create(uri);
    request.Method = "HEAD";
    request.KeepAlive = false;
    request.Timeout = Properties.Settings.Default.WebTimeoutDefault;

    using (HttpWebResponse response = (HttpWebResponse)request.GetResponse())
    {
        result = new HttpHeaderInfo();
        result.LastModified = response.LastModified;
        result.ContentType = response.ContentType;
        result.StatusCode = response.StatusCode;
        result.ContentLength = response.ContentLength;
    }
}
catch (WebException ex)
{
    // etc.
}

Это намного яснее, чем исходная форма. Также обратите внимание, что я перехватываю WebException , а не общий System.Exception . Вы должны перехватывать определенные типы исключений вместо того, чтобы перехватывать общие исключения и затем проверять их тип.

10
ответ дан 8 December 2019 в 13:46
поделиться

Другие указали Это потенциал потенциал проблема , но я хочу поднять его как , очень определенный Проблема: Ваше используемое утверждение делает вас не совсем хорошим в данный момент.

Когда вы пишете используемую оператор, подобное это:

SomeType x = value1;
using (x)
{
    x = value2;
}

Это значение1 , которое будет расположено в конце блока, не значение2 . В вашем коде ответ - это нулевой до блока; WEBRESPOSS Вы в конечном итоге с волей нет .

Вы должны видеть предупреждение об этом, вдоль этих строк:

Предупреждение CS0728: Возможно неправильное назначение для местных «Ответ», который это аргумент с использованием или заблокированным оператором. Утилизация вызова или Разблокировка произойдет по первоначальной стоимости местного.

Это предупреждение важно - прислушиваясь.

Оставив это в сторону, совершенно разумно поставить блок Thrue / Catch в используемом операторе ... но в этом случае он, вероятно, должен быть снаружи Оператор использования, позволяющий инициализировать Ответ переменная в подходящее время, чтобы ответ всегда был утилизирован. Я также рассмотрел бы использование нескольких блоков CALL, вызывающих общий метод, а не использование «многократно».

6
ответ дан 8 December 2019 в 13:46
поделиться

Это совершенно нормально. Вы обрабатываете исключение и не хотите, чтобы он был дальше, это просто отлично, и вложенная попытка / уловка / наконец-то не проблема. (Внутренне «используя», как это просто попытка / наконец.)

Обновление: прочитайте немного ближе, и я думаю, что вы на самом деле хотите использовать в блоке «Попробуйте» - строку, в которой вы фактически помещаете объект в Переменная «Ответ» - это то, где вы хотите начать блок «Использовать». Это на самом деле компилирует как есть?

1
ответ дан 8 December 2019 в 13:46
поделиться
Другие вопросы по тегам:

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