'using' C# 和 sharpdx 中的作用域

'using' scope in C# and sharpdx

这个问题与 C# 更相关,但我最近开始学习 sharpdx,我想出了两种初始化资源的方法。首先将资源(本例中的 Texture2D)存储为全局变量。然后在代码中为其赋值并将其传递给sharpdx的方法(以及向下传递给sharpdx封装的c++)

backBufferPtr = m_swapChain.GetBackBuffer<Texture2D>(0)
_renderTargetView = new RenderTargetView(m_device, backBufferPtr);

然后在调用它的 class 的 dispose 方法中对其调用 dispose,本质上是在 class.

的整个生命周期内保留该 Texture2D

另一种使用using语句:

using(Texture2D backBuffer = _swapChain.GetBackBuffer<Texture2D>(0))
{
    _renderTargetView = new RenderTargetView(_d3d11Device, backBuffer);
}

而且我想知道为什么第二个实际上有效。我在调试器中检查了它,只要我在 using 语句中停止

backBuffer.NativePointer
_renderTargetView.Resource.NativePointer

指向内存中的同一个对象。一旦我离开 using 语句 backBuffer 就被释放并且不再指向任何东西,但是 _renderTargetView.Resource 没有改变,并且仍然指向它在 using 语句中所做的对象。

我做了一个快速测试:

class innerClass
{
    public Texture2D someResource;
}
/****/
innerClass ic = new innerClass();

using (Texture2D t2 = m_swapChain.GetBackBuffer<Texture2D>(0))
{
     ic.someResource = t2;
}

这里 t2 和 ic.someResource 都被处理掉了,并且指向任何东西,只要我离开 using 块,这就是我最初期望它工作的方式。

现在,问题是:

1) 我是否应该假设,在第一个示例中,实际上是 sharpdx 的方法确保内部资源不会被处置,即使传递给它的 c# 对象确实处置了?如果 C# 决定覆盖该内存块,它不会在某个时候崩溃吗?

2) better/safer 传递此类资源的方式是什么? using 块,还是在开头声明它并在最后处理?

SharpDX 保留对底层图形资源的引用计数。因此,例如,当您获取对后台缓冲区的引用时:

Texture2D backBuffer = _swapChain.GetBackBuffer<Texture2D>(0)

然后获取相同底层资源的渲染目标视图:

_renderTargetView = new RenderTargetView(_d3d11Device, backBuffer);

您需要处理它们以及交换链以从 GPU 释放后台缓冲区资源。


What's better/safer way of passing such resources? using block, or declare it at the beginning and dispose at the very end?

我想这取决于用法,但据我所知,通常获取资源句柄的 class 会在其自己的 IDisposable 实现中处理它。