В C # using
оператор используется для детерминированного размещения ресурсов без ожидания сборщика мусора. Например, он может быть использован для:
Утилизируйте команды или соединения SQL,
Закрывайте потоки, освобождая основной источник как файл,
Бесплатные элементы GDI +,
и т.п.
Я заметил, что using
это все больше и больше используется в тех случаях, когда нечего распоряжаться, но когда вызывающей стороне просто удобнее написать using
блок, а не две отдельные команды.
Примеры:
MiniProfiler , написанный командой Stack Overflow, использует
using
для обозначения блоков в профиле:using (profiler.Step("Name goes here")) { this.DoSomethingUseful(i - 1); }
Одним из альтернативных подходов было бы иметь два блока:
var p = profiler.Start("Name goes here"); this.DoSomethingUseful(i - 1); profiler.Stop(p);
Другой подход заключается в использовании действий:
profiler.Step("Name goes here", () => this.DoSomethingUseful(i - 1));
ASP.NET MVC также выбран
using
для форм:<% using (Html.BeginForm()) { %> <label for="firstName">Name:</label> <%= Html.TextBox("name")%> <input type="submit" value="Save" /> <% } %>
Такое использование уместно? Как это оправдать, учитывая, что есть несколько недостатков:
Начинающие будут потеряны, так как такое использование не соответствует тому, которое объясняется в книгах и спецификации языка,
Код должен быть выразительным. Здесь страдает выразительность, поскольку надлежащее использование
using
состоит в том, чтобы показать, что позади есть ресурс, такой как поток, сетевое соединение или база данных, который должен быть освобожден без ожидания сборщика мусора.
источник
using
: последнее (напримерprofiler.Stop(p)
) утверждение не гарантируется для выполнения в условиях исключений и потока управления.Ответы:
Ваше последнее утверждение - «правильное использование использования - показать, что позади есть ресурс, такой как поток, сетевое соединение или база данных, которая должна быть освобождена без ожидания сборщика мусора», и причина, почему приведены в документации по интерфейсу IDisposable: http://msdn.microsoft.com/en-us/library/system.idisposable.aspx
Итак, если ваш класс использует какие-либо неуправляемые ресурсы, не имеет значения, когда вы можете или не хотите, чтобы GC происходил - он не имеет ничего общего с GC, поскольку неуправляемые ресурсы не GC'ed ( https: // stackoverflow. ru / questions / 3607213 / что означает «управляемый против неуправляемых ресурсов в сети» .
Таким образом , цель « используя» не избежать ожиданий на GC, это заставить выпуск этих неуправляемых ресурсов в настоящее время , до того , как экземпляр класса выходит из области видимости , и это Доработка называется. Это важно по причинам, которые должны быть очевидны: неуправляемый ресурс может зависеть от других неуправляемых ресурсов, и если они утилизируются (или завершаются) в неправильном порядке, могут возникнуть плохие вещи.
Таким образом, если класс, который создается в блоке using, использует какие-либо неуправляемые ресурсы, тогда ответ - да - это уместно.
Обратите внимание, что IDisposable не предписывает, что он предназначен только для освобождения неуправляемых ресурсов - просто это его основная цель. Это может быть так , что автор класса имеют некоторые действия , которые они хотят провести в жизни происходит в определенное время, и реализации IDisposable может быть способом получения , что должно произойти, но действительно ли , что элегантное решение является то , что может ответ только на индивидуальной основе.
В любом случае, использование «using» подразумевает, что класс реализует IDisposable, поэтому он не нарушает выразительность кода; это действительно дает понять, что происходит на самом деле.
источник
Использование
using
подразумевает наличиеDispose()
метода. Другие программисты будут предполагать, что такой метод существует на объекте. Следовательно, если предмет не является одноразовым, вы не должны использоватьusing
его.Четкость кода - это король. Либо опустите
using
, либо внедритеIDisposable
в объект.Похоже, что MiniProfiler использует
using
в качестве механизма «забор» в профилируемом коде. В этом есть некоторая заслуга; предположительно, MiniProfiler либо вызываетDispose()
останов таймера, либо таймер останавливается, когда объект MiniProfiler выходит из области видимости.В более общем случае вы вызываете,
using
когда какая-то финализация должна выполняться автоматически. В документацииhtml.BeginForm
говорится, что когда метод используется вusing
операторе, он отображает закрывающий</form>
тег в концеusing
блока.Это не обязательно означает, что это все еще не злоупотребление.
источник
IDisposable
/Dispose()
несмотря на то, что не имеет ничего, что можно было бы распоряжаться в том смысле, который описывает OP?Dispose
что требуется для того,using
чтобы вообще иметь смысл (независимо от того, уместно ли это). Примеры OP все реализуютDispose
, не так ли? И IIUC, вопрос в том, правильно ли использовать эти классыDispose
, а не какой-то другой метод (например,Stop()
для MiniProfiler).using
безопасен от ошибок и исключений. Это гарантируетDispose()
, что вызов будет вызван независимо от ошибок, которые делает программист. Это не мешает перехвату или обработке исключений, ноDispose()
метод выполняется рекурсивно вверх по стеку, когда генерируется исключение.Объекты, которые реализуют,
IDispose
но им нечего распоряжаться по завершении. В лучшем случае, будущее проверяет их дизайн. Чтобы вам не приходилось реорганизовывать исходный код, тогда в будущем им необходимо что-то распоряжаться.источник