2

から派生した CLI C++ クラスを作成しようとしていますHashAlgorithmHashAlgorithmメソッドがありvirtual Dispose(bool)ます。予約済みのキーワードであるDisposeというコンパイル エラーが発生するため、メソッドをオーバーライドできません。dispose私がオンラインで読んだことから、ファイナライザーと dtor を追加するだけで、コンパイラーが他のすべてを処理します。私はこれを行い、コードはコンパイルされます。使用しようとすると、次のエラーが表示されます。

System.TypeLoadException: Declaration referenced in a method implementation cannot be a final method

コンパイラが生成したコードを見ると、この封印されたキーワードが問題の原因であると思われるメソッドに置かれていることがわかります。メソッドは基本クラスに既に存在するため、Dispose実際にはまったく必要ありません。これを回避する方法についてのアイデア。

public sealed override void Dispose()
4

1 に答える 1

2

ご指摘のとおり、C++/CLI では ~ClassName と !ClassName を実装し、C++/CLI コンパイラは Dispose(void) と Dispose(bool) を書き込みます。

HashAlgorithm から派生させてみたところ、破棄とファイナライズの両方を機能させることができました。おそらく、いくつかのメソッドを宣言する方法に微妙な違いがあります。

ここに私のテストコードがあります:

public ref class CppDispose : HashAlgorithm
{
private:
    ~CppDispose() { Debug::WriteLine("~CppDispose"); }
    !CppDispose() { Debug::WriteLine("!CppDispose"); }

protected:
    virtual void HashCore(array<Byte>^ aray, int ibStart, int cbSize) override { }
    virtual array<Byte>^ HashFinal() override { return nullptr; }

public:
    virtual void Initialize() override { }
};

int main(array<System::String ^> ^args)
{
    {
        CppDispose foo;

        Debug::WriteLine("Disposing: ");
    }

    {
        CppDispose^ foo = gcnew CppDispose();

        Debug::WriteLine("Finalizing: ");
        foo = nullptr;
        GC::Collect();
    }

    return 0;
}

出力:

廃棄:
~CppDispose
ファイナライズ:
!CppDispose

舞台裏で何が起こっているかを確認できるように、C++/CLI コンパイラが作成したメソッドを C# 構文に逆コンパイルしたものを次に示します。この場合、親クラスには Dispose(void) が実装されているため、ここでは再実装されていません。

[HandleProcessCorruptedStateExceptions]
protected override void Dispose([MarshalAs(UnmanagedType.U1)] bool flag1)
{
    if (flag1)
    {
        try
        {
            this.~CppDispose();
        }
        finally
        {
            base.Dispose(true);
        }
    }
    else
    {
        try
        {
            this.!CppDispose();
        }
        finally
        {
            base.Dispose(false);
        }
    }
}

protected override void Finalize()
{
    this.Dispose(false);
}
于 2013-01-17T00:26:51.437 に答える