C++ 中本地类的用法功能
我看到 C++ 函数中内部结构的一些用法。
有一个通用接口IBase。这是代码草案。
class IBase
{
virtual Method()=0;
}
vector<IBase*> baseList;
然后一个函数根据该IBase定义一个内部类,然后将内部类对象压入baseList中。
void func()
{
struct Object : public IBase
{
virtual Method()
{
// Method of Object in func
}
}
IBase* base = new Object();
baseList->push(base);
}
这似乎是一个奇怪的用法,但却是消息/事件创建模式的一个很好的实现。
其他线程可能使用此 baseList 来处理传入事件。
“struct Object”的内部结构的范围是什么?这很有趣。有一些文件谈论这个吗?
I see some usage of internal struct in c++ function.
There is a common interface IBase. Here is the draft code.
class IBase
{
virtual Method()=0;
}
vector<IBase*> baseList;
Then a function defined an internal class based on that IBase, and then push the internal class object into the baseList.
void func()
{
struct Object : public IBase
{
virtual Method()
{
// Method of Object in func
}
}
IBase* base = new Object();
baseList->push(base);
}
It seems a strange usage, but a nice implementation of message/event creation pattern.
Other threads maybe use this baseList to handle the incoming event.
What's the scope of internal struct of "struct Object"? It's very interesting. Is there some documents talking about this?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
本地类的范围是定义它们的函数。但这本身并不有趣。
本地类的有趣之处在于如果它们实现了某个接口(就像您的代码那样),那么您可以创建它的实例(使用),从而使实现可以通过基类指针访问,甚至可以在函数外部访问。
new
)并返回它们(例如,如 std::vector关于局部类的其他一些事实:
它们不能定义静态成员变量。
它们无法访问封闭函数的非静态“自动”局部变量。但它们可以访问
静态
变量。它们可以在模板函数中使用。
如果它们在模板函数内定义,则它们可以使用封闭函数的模板参数。
本地类是最终的,这意味着函数外部的用户不能从本地类派生到函数。如果没有本地类,您必须在单独的翻译单元中添加未命名的命名空间。
本地类用于创建trampoline 函数,通常称为thunk 。
编辑
标准 (2003)
9.8 局部类声明 [class.local]
The scope of the local classes is the function in which they're defined.But that isn't interesting in itself.
What makes local classes interesting is that if they implement some interface (like your code does), then you can create instances of it (using
new
) and return them (for example, asstd::vector<IBase*>
), thereby making the implementation accessible through the base class pointer even outside the function.Some other facts about local classes:
They cannot define static member variables.
They cannot access nonstatic "automatic" local variables of the enclosing function. But they can access the
static
variables.They can be used in template functions.
If they are defined inside a template function, then they can use the template parameters of the enclosing function.
Local classes are final, that means users outside the function cannot derive from local class to function. Without local classes, you'd have to add an unnamed namespace in separate translation unit.
Local classes are used to create trampoline functions usually known as thunks.
EDIT
Some references from the Standard (2003)
9.8 Local class declarations [class.local]
\4.局部类不应有静态数据成员。
但是你可以这样做,在本地类内部
_local::Count 可用于读取和写入静态变量
-aydin
\4. A local class shall not have static data members.
BUT you can do this, inside of a local class
_local::Count can be used to read and write the otherwise static variable
-aydin
这是普通的C++。
struct Object
的范围仅为函数func
。但是,您仍然可以使用这种类型的对象,而无需知道它们是什么具体类型,因为它们继承自IBase
。这用于封装实现。This is normal C++. The scope of
struct Object
is only the functionfunc
. However, you can still use objects of this type without knowing which concrete type they are, since they inherit fromIBase
. This is used to encapsulate implementation.Jason Turner 在他的 CppCon 演讲中介绍了本地类的一个非常有趣的用法,该演讲重点关注用 C++17 编写 Commodore 64 游戏。他展示了如何在功能级别上使用 RAII 原则。
他基本上在返回此类实例的函数中的本地类的构造函数中建立了不变量。因此,不变量的持续时间由返回对象的生命周期控制。它与
std::lock
之类的 RAII 包装器所做的非常相似,只是略有不同。您可以在此处查看相应部分,但我喜欢 他的表现并建议从头到尾看一遍。
A very interesting use of a local class is presented by Jason Turner in his CppCon talk focused on programming of Commodore 64 game in C++17. He shows how to use the RAII principle on the function level.
He basically establishes invariants in the constructor of a local class in a function returning an instance of this class. The invariants duration is thusly controlled by the lifetime of the returned object. It is quite similar to what RAII wrappers like
std::lock
do, just slightly different.You can see the appropriate part here, but I love his performance and recommend to see it all the way through.