Управление ресурсами: ключевое слово use

В этом разделе описываются ключевое слово use и using функция, которые могут управлять инициализацией и выпуском ресурсов.

Ресурсы

Ресурс термина используется несколькими способами. Да, ресурсы могут быть данными, которые использует приложение, такие как строки, графики и подобные, но в этом контексте ресурсы ссылаются на ресурсы программного обеспечения или операционной системы, такие как контексты графических устройств, дескрипторы файлов, сетевые и подключения к базе данных, объекты параллелизма, такие как дескриптор ожидания и т. д. Использование этих ресурсов приложениями включает приобретение ресурса из операционной системы или другого поставщика ресурсов, за которым следует более поздний выпуск ресурса в пул, чтобы его можно было предоставить другому приложению. Проблемы возникают, когда приложения не освобождают ресурсы обратно в общий пул.

Управление ресурсами

Чтобы эффективно и ответственно управлять ресурсами в приложении, необходимо быстро и предсказуемо освободить ресурсы. Платформа .NET Framework помогает сделать это, предоставив System.IDisposable интерфейс. Тип, реализующий System.IDisposableSystem.IDisposable.Dispose метод, который правильно освобождает ресурсы. Хорошо написанные приложения гарантируют, что вызывается быстро, System.IDisposable.Dispose когда любой объект, содержащий ограниченный ресурс, больше не нужен. К счастью, большинство языков .NET обеспечивают поддержку, чтобы упростить эту задачу, и F# не является исключением. Существует два полезных языковых конструкции, поддерживающие шаблон удаления: use привязку и using функцию.

использование привязки

Ключевое слово use имеет форму, которая напоминает привязкуlet:

использование выражения значений =

Он предоставляет те же функции, что let и привязка, но добавляет вызов Dispose к значению, когда значение выходит из область. Обратите внимание, что компилятор вставляет значение null проверка в значение, чтобы, если значение равноnull, вызов Dispose не выполняется.

В следующем примере показано, как автоматически закрыть файл с помощью use ключевое слово.

open System.IO

let writetofile filename obj =
   use file1 = File.CreateText(filename)
   file1.WriteLine("{0}", obj.ToString() )
   // file1.Dispose() is called implicitly here.

writetofile "abc.txt" "Humpty Dumpty sat on a wall."

Несколько экземпляров use удаляются в обратном порядке, в котором они объявлены. То есть первый use будет последним выпуском.

Примечание.

Вы можете использовать use в выражениях вычислений, в этом случае используется настраиваемая версия use выражения. Дополнительные сведения см. в разделе "Последовательности", "Асинхронные выражения", "Выражения задач" и "Вычисления".

использование функции

Функция using имеет следующую форму:

using (expression1) function-or-lambda

using В выражении выражение1 создает объект, который должен быть удален. Результат выражения1 (объект, который должен быть удален) становится аргументом, значением для функции или лямбда-функции, которая ожидает один оставшийся аргумент типа, который соответствует значению, созданному выражением expression1, или лямбда-выражение, которое ожидает аргумент этого типа. В конце выполнения функции среда выполнения вызывает Dispose и освобождает ресурсы (если значение не имеет nullзначения, в этом случае вызов dispose не выполняется).

В следующем примере показано using выражение с лямбда-выражением.

open System.IO

let writetofile2 filename obj =
    using (System.IO.File.CreateText(filename)) ( fun file1 ->
        file1.WriteLine("{0}", obj.ToString() )
    )

writetofile2 "abc2.txt" "The quick sly fox jumps over the lazy brown dog."

В следующем примере показано using выражение с функцией.

let printToFile (file1 : System.IO.StreamWriter) =
    file1.WriteLine("Test output");

using (System.IO.File.CreateText("test.txt")) printToFile

Обратите внимание, что функция может быть функцией, которая уже применяет некоторые аргументы. Это действие представлено в следующем примере кода: Он создает файл, содержащий строку XYZ.

let printToFile2 obj (file1 : System.IO.StreamWriter) =
    file1.WriteLine(obj.ToString())

using (System.IO.File.CreateText("test.txt")) (printToFile2 "XYZ")

Функция using и привязка use практически эквивалентны тому же способу. Ключевое слово using обеспечивает больший контроль над Dispose вызовом. При использовании вызывается в конце выражения функции или лямбда-выражения; при использовании usingDisposeuse ключевое слово Dispose вызывается в конце содержащего блока кода. Как правило, вместо функции следует использовать useusing .

См. также