引用C#中父作用域中的对象是可能的
本文关键字:对象 作用域 引用 | 更新日期: 2023-09-27 18:00:42
我有一个类,它创建了一个"数据持有者"对象,然后用一些修饰符类修改这个对象,类似于:
public class Process {
public void Run() {
var dataHolder = new DataHolder();
var firstModification = new FirstModification(dataHolder);
firstModification.Run();
var secondModification = new SecondModification(dataHolder);
secondModification.Run();
//etc.
}
}
public class FirstModification {
DataHolder data_holder;
public FirstModification (DataHolder dh) {
data_holder = dh;
}
public void Run() {
// do something with data_holder
}
}
public class SecondModification {
// etc.
}
在这段代码中,每个修改构造函数都必须接收dataHolder
作为参数,以及相应的样板,在修改器类中重复代码。
因此,如果可能和/或建议的话,我希望每个修饰符对象都"已经知道"Process.Run()
方法(可以说是其"父作用域")中存在活动的dataHolder
对象,而无需将其作为参数传递给修饰符构造函数。
编辑:我正在尝试实现管道(又名管道和过滤器)设计模式,灵感来自这里和这里的描述。
谢谢你的帮助!
因此,如果可能和/或建议的话,我希望每个修饰符对象都"已经知道"Process.Run()方法(可以说是其"父作用域")中存在活动的dataHolder对象,而无需将其作为参数传递给修饰符构造函数。
可能吗?是的,通过线程本地变量来维护"该线程的当前DataHolder
"(甚至只是一个简单的静态变量)。
推荐?不,我不会这么说。我认为你现在没有错——你认为把一切都隐含起来会有什么好处?
没有什么可以让你回到堆栈并在调用方法中找到局部变量。。。
您必须以某种方式关联实例
var firstModification = new FirstModification()
等等。与实际数据进行比较。
目前的做法还不错。如果您希望修改实例能够访问"父作用域",则必须将父对象引用传递给它们。这实际上为他们提供了比他们实际需要的更多的对父对象的访问,我不鼓励这样做。
如何对Modifier类进行超类化,并使DataHolder对象作为静态变量从Process类中可用?
public class SuperModifierClass
{
DataHolder dataHolder;
public SuperModifierClass()
{
dataHolder = Process.DataHolder;
}
}
public class FirstModifier
{
public FirstModifier() : base() // Is base called implicitly by default? I forgot...
{
}
}
另一种选择是通过MEF和Unity(谷歌这些术语)等框架来研究控制权的倒置。这些方法本质上允许您注册对象,这些对象可以在实例化将它们作为参数的新类时自动加载。你会说"好吧,如果有人需要DataHolder对象,就用这个"。当你通过这样的框架实例化修改类时,它所调用的"容器"实际上通过询问它是否已经注册并获取注册的实例来解析参数。
使用ref
关键字作为参数。
...
var firstModification = new FirstModification(ref dataHolder);
...
public FirstModification (ref dataHolder dh) {
// Make changes to dh
}
...
这将把对Process类中dataHolder对象的引用传递给FirstModification方法。