土曜日, 7月 12, 2025
土曜日, 7月 12, 2025
- Advertisment -
ホームニューステックニュースJavaScript の using と DisposableStack#defer で Go の defer 風

JavaScript の using と DisposableStack#defer で Go の defer 風



JavaScriptのExplicit Resource Managementという提案では using という構文が注目されがちな気がする。しかし実は構文以外にもいくつかのビルトインが追加される。

こないだExplicit Resource Managementで追加されたビルトインをSafariに実装したときに「へ〜」と思ったのでよくありそうな使い方を紹介する。

Go の defer

Go の defer をご存知だろうか。たとえばこういうコードがあるとする。

func main() {
    f := createFile("/tmp/defer.txt")
    defer closeFile(f)
    writeFile(f)
}

main 関数内の2行目では defer closeFile(f) を実行している。ここで、この closeFile(f)createFile の直後には呼び出されない。代わりにこのmain関数のスコープを抜ける時、つまりここでは writeFile(f) の直後に呼び出される。

defer を使うことでリソースの確保と解放をコード上の近い場所に書くことができる。

JavaScript の usingDisposableStack#defer

JavaScriptでもExplicit Resouce Managementによって追加される using という構文と DisposableStack というビルトインを使うことによって、Goのdeferのようにリソースの確保と解放の処理を記述できる。

たとえば、こういうふうに書くことができる。

function main() {
    using stack = new DisposableStack();

    const f = createFile("/tmp/defer.txt");
    stack.defer(() => { closeFile(f); });
    writeFile(f);
}

このコードは前述したGoのdeferの例をそのままJavaScriptに移植したものだ。

まず main 関数の先頭で using 構文を使って DisposableStack のインスタンス stack を作る。こうすると main 関数のスコープを抜ける時に stack[Symbol.dispose] 関数が呼び出されるようになる。これは using 構文の機能である。

DisposableStack は内部にスタックを持つデータ構造だ。スタックのエントリはそれぞれ [Symbol.dispose] 関数を持つオブジェクトである。そして DisposableStack 自体の [Symbol.dispose] 関数はスタック内の全てのエントリの [Symbol.dispose] 関数を呼び出す。

stack.defer(fn) は、 [Symbol.dispose] が呼び出された時に fn を呼び出すだけの disposable stack を新たに作成して stack の内部スタックに積む。

つまり、main 関数のスコープを抜ける時にはまず stack[Symbol.dispose] が呼び出される。その呼び出しによって stack の内部スタック内の全てのオブジェクトの [Symbol.dispose] が呼び出される。この時スタック内には () => { closeFile(f); } を呼び出すだけのオブジェクトが存在しているため、その関数が呼び出される。

このように usingDisposableStack を使うことでJavaScript においても Go の defer のようにリソースの確保と解放の処理を記述できる。

まとめ

  • Go の defer を使うことでリソースの確保と解放をコード上の近い場所に置ける
  • JavaScript でも Explicit Resource Management 提案の using 構文と DisposableStack#defer を使うと、似たように書くことができる

参考



Source link

Views: 0

RELATED ARTICLES

返事を書く

あなたのコメントを入力してください。
ここにあなたの名前を入力してください

- Advertisment -