什么是C ++等效的java.lang.Object x = new Foo()? [英] What is the C++ equivalent of java.lang.Object x = new Foo()?

查看:134
本文介绍了什么是C ++等效的java.lang.Object x = new Foo()?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

什么是C ++等价的 java.lang.Object x = new Foo()

What is the C++ equivalent of java.lang.Object x = new Foo()?

推荐答案

在C ++中没有类似的东西,尝试用C ++编写Java也是毫无意义的。话虽如此,我将从尝试模仿尽可能多的分配特征和声明的精神的角度看待这一点。每种方式我建议有缺点和局限性。前两个不是真正的成语C ++,但重要的是要知道他们看到最后两个问题解决了什么问题。

There is no equivalent of this in C++ and it would be pointless to attempt to program Java in C++. That being said, I will approach this from a perspective of attempting to mimic as much of the assignment characteristics and spirit of the statement as possible. Each way I will suggest has downsides and limitations. The first two are not truly idiomatic C++ but it's important to know about them to see what problems the last two solved.

1。

让我从最基本和最不实用的一个void指针开始:

Let me start with the most basic and least useful, a void pointer:

void* foo = new Foo();

任何东西都可以从new操作符赋值给一个void指针,作为new,placement new等返回一个void指针。缺点应该是显而易见的:丢失类型信息关于指向的对象。一个,C ++缺乏反射或任何手段来询问对象。你必须保持类型信息在你的头,并使用来回投入实际使用它。因为没有类型安全的方法来从一个void指针转换,可能会出现欢闹。

Anything can be assigned to a void pointer from the new operator as new, placement new and the like always return a void pointer. The downsides should be obvious: loss of type information about the object pointed at. For one, C++ lacks reflection or any means of interrogating the object. You'd have to keep the type information in your head and use casting back and forth to actually use it. Since there's no type-safe way to cast from a void pointer, hilarity could ensue.

如果这是一个函数的返回类型:

If this were a return type from a function:

void* foo = some_function( _arg0 );

使用您的代码的任何作者都需要弄清楚不幸的是,通常情况下,他们的事情应该发生和你,作者,认为应该从函数返回是非常不同的。

any author using your code would need to figure out what should happen. Unfortunately, often times what they thing should happen and what you, the author, think should be returned from a function are very different.

2。 C-style Unions

如果你想限制自己支持的N类型,而不是java.lang.Object可以处理的无限类型, 联盟。这些可以在同一存储器空间上保存一组预定义的值类型,只要它们是POD数据类型 。联盟缺少两个非常重要的事情:知道分配了哪个值以及保存非POD类型的能力。这完全规定它们用于具有任何类型的功能的任何对象,例如 std :: string

If you want to restrict yourself to N types which are supported instead of infinite types that java.lang.Object can handle then there are unions. These can hold a set of pre-defined value types on the same memory space as long as they are POD datatypes. Unions lack two very important things: the ability to know which value was assigned and the ability to hold non-POD types. This completely rules them out for use with any object with any sort of functionality such as std::string.

要澄清上面实际意味着什么:

To clarify what the above actually means:

union myType{
    int a;
    char b[4];
};

如果我在myType实例的b部分中设置第一个字符,还设置int的第一个字节为相同的值。在C ++中,这些仅仅是对内存破解和极低级别的编程有用的(认为嵌入式等)。它们不是惯用的C ++。

If I set the first char within the "b" portion of an instance of "myType" then I also am setting the first byte of the int to that same value. In C++ these are really only useful for memory hacks and extremely low level programming (think embedded and the like.) They are not idiomatic C++.

3。 Boost :: Any

现在,如果你真的想要一个我可以持有任何东西,那么使用Boost::Any 。这可以保存任何对象而不破坏很多类型信息,这是非常有用的。 Boost文件的状态比我的目的更好。从Any的介绍部分获取:

Now, if you truly want a "I can hold anything" then use a Boost::Any. This can hold any object without destroying a lot of type information which is so useful. The Boost documents state better than I in their purpose. Taken from the introduction section of Any:


有时候,泛型(在一般意义上而不是基于模板的编程)类型是必需的:真正变量的变量,容纳许多其他更具体类型的值,而不是C ++的正常严格和静态类型。

There are times when a generic (in the sense of general as opposed to template-based programming) type is needed: variables that are truly variable, accommodating values of many other more specific types rather than C++'s normal strict and static types.

想想任何解决与void指针相关的许多问题,例如丢失所包含对象的信息,以及安全地转换为正确类型的能力。

Think of Any solving many of the problems associated with a void pointer, such as loss of information about the contained object and the ability to safely cast to proper types.

4。 Boost :: Variant

Boost :: Variant 解决了同一类型的问题,而不会丢失对象信息。此外,它可以与非POD类型的对象一起使用。

Boost::Variant solves the same type of problem of that of a union without losing object information. Moreover it can be used with non-POD type objects. As the documentation states it best:


典型的解决方案具有对象的动态分配,随后通过一个共同的基本类型虚拟基本类 Hen01 或更多危险,空白*)。具体类型的对象然后可以通过多态下行构造(例如,dynamic_cast,boost :: any_cast等)来检索。

Typical solutions feature the dynamic-allocation of objects, which are subsequently manipulated through a common base type (often a virtual base class Hen01 or, more dangerously, a void*). Objects of concrete type may be then retrieved by way of a polymorphic downcast construct (e.g., dynamic_cast, boost::any_cast, etc.).

然而,这种解决方案是非常容易出错的,原因如下:

However, solutions of this sort are highly error-prone, due to the following:


  1. 无法在编译时检测到downcast错误。因此,不正确使用downcast结构将导致错误只能在运行时检测。

  2. 添加新的具体类型可能会被忽略。如果将新的具体类型添加到层次结构中,则现有的向下代码将继续按原样工作,完全忽略新类型。因此,程序员必须在多个位置手动定位和修改代码,这通常会导致难以找到的运行时错误。


编辑:

重新组织以显示我回答OP时我的想法的原因和原因。我也在下面提出了意见。

Reorganized to show the what and the why of my thoughts when I answered the OP. I've also addressed comments below.

这篇关于什么是C ++等效的java.lang.Object x = new Foo()?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆