D构造函数问题
/// module g.d
class world
{
atlasHandler atlas;
void do()
{
atlas = new AtlasHanlder();
elf e = new elf(atlas);
}
}
/// module 'objects.d'
class atlasHandler{}
class elf
{
this(atlasHandler atlas)
{
assert(atlas !is null); //正常
assert(g.world.atlas !is null); //崩溃
writefln("atlas [%p] vs g.world.atlas [%s]", atlas, g.world.atlas);
// 读g.world.atlas时,崩溃.
}
}
world
为null
是因为未构造成功
.构造器内部有段错误
.
也像是你原段错误
的来源.你在构造器
中有循环引用
.即,你在构造全局世界实例
,它又构造了访问
构造器尚未完成的全局世界
引用的elf
实例,因此全局世界引用
仍为空.
如果正在构建世界
,且需要访问它,则可:
1,用闲着的析构器
初化世界,然后在它上面调用setup
方法干构造器的活;
2,从世界
构造器中传递this
给所有需要它的构造器
.
类似:
import std.stdio : writeln;
class Foo {
Bar b;
this() { b = new Bar; }
void sayMyName() { writeln("哈哈."); }
}
class Bar {
this() { f.sayMyName(); }
}
Foo f;
void main()
{
f = new Foo;
}
与模块无关.它是引用
自身.
在构造器
返回前,构造实例的引用
为null
.与在模块,函数域等
都没有关系.如果未构造
成功(段错误,抛的异常,断定失败等),则引用
始终为null
.
引用
不是实例
.它是实例的指针
.已调用构造器
时实例
有效,因为this
引用必须有效.考虑普通函数调用:
T newT() {
T t = allocT();
t.construct(t);
return t;
}
T g = newT();
如果t.construct
抛或崩溃,则不会执行return t
,也不会初化g
.
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· 没有Manus邀请码?试试免邀请码的MGX或者开源的OpenManus吧
· 【自荐】一款简洁、开源的在线白板工具 Drawnix
· 园子的第一款AI主题卫衣上架——"HELLO! HOW CAN I ASSIST YOU TODAY
· Docker 太简单,K8s 太复杂?w7panel 让容器管理更轻松!