我应该使用的dynamic_cast 用于复制?
-
06-09-2019 - |
题
更新1:
校正的无义代码!感谢评论,我提出的第一个片段的散列,糟糕。
更新2:
也更新问题的标题,由于采用的dynamic_cast的已经指出作为不需要通过答案。
我想在这里实现的是使用强类型的深副本;我希望能够到的Class2复制到Class2中的另一个实例;不过,我也想使用copyTo函数,即是基础Class1的。这个想法来自我的C#的经验,在平时我只希望做回普通型(见C#代码段)。
void Class1::CopyTo(Class1 *c1)
{
// Write data in to c1 from this instance.
c1->exampleData = exampleData;
}
// Class2 inherits Class1
Class2 *Class2::Copy()
{
Class2 *c2a = new Class2();
CopyTo(c2a);
Class2 *c2b = dynamic_cast<Class2*>(c2a);
return c2a;
}
和这里的路我会因此它在C#中:
public class Class1
{
T Copy<T>()
where T : Class1
{
/* Can't remember the best way to do this in C#;
* basically if T was Class2 this would need to create
* a new instance of that class, and the same goes for
* Class1. */
T copy = createNewInstance();
// Copy the data from this to 'copy'.
copy.exampleData = exampleData;
return copy;
}
}
现在,相比于C#片段中,C ++代码段感到臭。是否有可能做到这一点没有指针,或者是这样的最佳实践?
解决方案
我不知道你正在努力实现的,因为代码仍然没有太大的意义是什么。然而,我认为以下应接近你想要做什么。请注意,我的不的使用堆内存:这是没有必要的,它会泄漏内存
template <typename T>
T Class1::Copy()
{
T instance;
CopyTo(&instance);
return instance;
}
此工作,因为你传递一个(多晶型)指针instance
到CopyTo
的Class1
方法。
然后,你可以调用这样的代码:
Class2 x1;
// Fill x1
Class2 x2 = x1.Copy<Class2>();
然而,这段代码的还是的味道,因为它是不地道的C ++:在C ++中,你通常会写一个拷贝构造函数来代替。确实存在后期绑定Copy
方法,但他们很少需要,并且上面没有后期绑定(但也不是你的C#代码)。
其他提示
我不清楚你在问什么,但是要知道,当你说:
Class2 *c2 = dynamic_cast<Class2*>(c1);
剧组的结果可能是NULL,你必须检查这一点。
您应该对代码片段多一点的工作。 <击> GetSomethingCopy是创建被传递给CopyTo从类型的Class2的指针。 CopyTo从试图调用一个从未被初始化的接收指针的成员函数:分段错误和程序死亡击>
即使未杀死的应用程序,你想的的dynamic_cast 的从Class2中*到CLASS2 *这是几乎什么都不做。如果您打算在铸造从CopyTo从返回的值是什么,你要知道,你不能使用无效dynamic_cast的*。您必须更改签名CopyTo从返回的Class1(使您可以在以后投的话)或就作废了使用的static_cast *。
请注意,要么Copy是在Class1的一个虚拟函数是在等级2中执行的事实,并创造一个等级2对象,否则,返回的元件将不会是一个等级2,而是Class1的。
的方法CopyTo的名称是混乱的,因为它不复制的到参数,而是从参数。
和这一切后,我还是不知道你在问什么。你会在哪里要使用堆栈内存?你可以通过分配元件的功能的堆栈,但返回指针/参考的堆栈分配的元件再次是分段故障:当函数结束对象将被破坏,接收机将留下一个悬挂指针/参考。
现在,如果你的问题是你是否可以在堆栈中分配元素上使用的dynamic_cast更多的理论,你可以(前提是等级2的Class1从继承):
void f()
{
Class2 c2;
Class1 &c1 = c2; // c1 is a Class1 reference to a Class2 object
dynamic_cast<Class2&>(c1).class2method();
// or:
dynamic_cast<Class2*>(&c1)->class2method();
}
如果您更新代码,在发布这个答案评论让我发现和纠正它在今晚。
这代码是没有意义的陈述......反正我“猜”,你可以使用静态投,如果你没有使用一个void *作为回报呢?
确定现在的代码是有意义的。
您不需要任何动态转换,它已经是类型的Class2。
在您的CopyTo从功能,你会返回一个指针,是在栈上创建一个对象 - 这是不可能的,因为对象在将被破坏的指针指向函数返回时,
在回答你的问题,你可以在一个指针或参考使用dynamic_cast
。在你的情况,我可能会分配给使用动态new
返回的对象,而不是在堆栈上,然后就可以放心地返回一个指针。但是我倾向于寻找使用dynamic_cast
作为一个潜在的代码的气味,以及应使用一个虚拟函数的标志。
没有,将dynamic_cast仅适用于指针和引用。你可以不返回任何你在栈上分配安全无论如何,所以我不知道你是如何打算修改代码在这种情况下。
嗯,现在的问题是显而易见的。答案是技术上不,不是withh的dynamic_cast <>,但我真的没有看到你为什么会想也无妨。看来你只是想
void Class1::CopyTo(Class1& c1)
{
// Write data in to c1 from this instance.
c1.SomeIntValue = SomeIntValue;
}
// Class2 inherits Class1
Class2* Class2::Copy()
{
Class2 *c2 = new Class2();
CopyTo(*c2);
return c2;
}
//or more idiomatic
Class2 Class2::Copy()
{
Class2 c2
CopyTo(c2);
return c2;
}