调用类析构函数时出现InvalidMemoryOperationError @

时间:2015-01-21 14:33:46

标签: d

计划是在调用类析构函数时使用模板记录消息,但似乎不可能。任何建议或解释将不胜感激。

import std.stdio;
import std.datetime;

class Test
{
    this()
    {
        struct Start
        {
            string filename;
        }
        Message!(Start)(Start("one.txt\n"));
    }

    ~this()
    {
        struct Stop
        {
            string filename;
        }

        Message!(Stop)(Stop("stop one.txt\n"));  // > core.exception.InvalidMemoryOperationError@(0)
        // auto t = Clock.currTime().toISOString(); // > core.exception.InvalidMemoryOperationError@(0
    }
}

unittest
{
    auto t = new Test();
}

struct Message(T)
{
    this(T message)
    {
        _time = Clock.currTime().toISOString();
        writefln("%s: %s", _time, message.filename);
    }
    string _time;
}

1 个答案:

答案 0 :(得分:3)

GC运行时不允许分配GC内存。由于类析构函数通常由GC运行,因此您不应该在那里使用它。

值得注意的是,在类析构函数中不允许通过引用访问其他GC成员,因为对象的成员可能与对象本身同时被释放,因此在该上下文中不可用。

所以诀窍是摆脱toISOString调用和对struct.toString的隐式调用。

这会更好用:

struct Message(T)
{
    this(T message)
    {
        auto time = Clock.currTime();
        writefln("%d:%02d:%02d %s(%s)",
          time.hour, time.minute, time.second,
          T.stringof, message.filename);
    }
}

通过在组件中的writefln中构建字符串而不是依赖于返回新字符串的函数,我们停止分配,防止异常。