将可选属性表示为C ++类成员 [英] Represent an optional attribute as a C++ class member

查看:67
本文介绍了将可选属性表示为C ++类成员的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在基于架构生成C ++代码。存在实体,每个实体包含一个或多个属性,每个属性具有对应的数据类型。现在的问题是这些属性中的一些是可选的,这意味着它们不必成为类声明的一部分。但是,在C ++中,某些东西要么是类的成员,要么不是类的成员,没有诸如可选数据成员之类的概念。

I am generating C++ code based on a schema. There are entities and each entity contain attribute(s) with each attribute having a corresponding data type. Now the problem is some of these attributes are "optional", meaning that they do not have to be part of the class declaration. However, in C++, something is either a member of class or not a member of class, there is no concept such as "optional data member".

实体是类名,属性是类成员。我不确定如何表示现有C ++概念中标记为可选的属性。

Entities will be the class names, and attributes will be the class members. I am not sure how I can represent attributes marked as "optional" the existing C++ concepts.

推荐答案

典型答案是 std :: optional 。这是表达模型中可能存在或可能不存在的值的语义上准确的方法。

The canonical answer is std::optional. It is a semantically accurate way to express a value that might or might not exist in a model.

创建此类模型时,对于架构中的每个可选字段,您都可以生成相应的 std :: optional 包装的条目。然后,在反序列化时,可以使用 std :: none 标记缺少的条目,并且在访问过程中,客户端代码必须检查实际值 1 的存在。

When creating such a model, for each optional field in a schema, you generate a corresponding std::optional-wrapped entry. Then, when deserializing, you can use std::none to mark a missing entry, and it during accessing, the client code must check for the existence of actual value1.

如果对象很大,并且您要避免不必要地存储空白 2 ,下一个替代方法是 std :: unique_ptr

If your objects are large, though, and you want to avoid storing the empty space unnecessarily2, the next alternative is std::unique_ptr. It has a downside of having pointer semantics, but otherwise remains a valid tool for such a case.

如果成员非常是动态的,例如,它具有指针语义的缺点。可能的设置是几十个或几百个,但是典型的利用率只有少数几个,键值存储(例如 std :: map )可能是一个更好的主意;那么您就只能存储一种类型的值。将 std :: variant 用作地图值类型可能会有所缓解,这为您提供了多种可能性之一,或者 std ::任何,可以有效地容纳任何东西,同时又失去类型安全性。

If the members are very dynamic, e.g. the possible set is in dozens or hundreds, but typical utilization will see just a few, a key-value store (such as std::map) might be a better idea; then you're limited to store just one type of a value. This might be mitigated a bit with std::variant being used as the map value type, which gives you one of many possibilities, or std::any, which can effectively hold anything while losing type safety.

最终的决定将取决于您的确切型号和使用特性。

The decision will ultimately depend on your exact model and usage characteristics.

1 如果客户端代码期望 T ,并且对字段的访问使它们具有 optional< T> ,展开步骤将/将检查实际值的存在。这是使用可选的主要原因。

1 If the client code expects T, and the access for a field gives them optional<T>, the unwrapping step will/shall check for the existence of an actual value. This is the main reason optional is used.

2 sizeof(optional< S>)通常为 sizeof(S)+ 1 ,但由于对齐规则而可能变大。本文的 Performance& Memory 部分很好地展示了它。

2 sizeof(optional<S>) will most commonly be sizeof(S) + 1, but can get bigger because of the alignment rules. Performance&Memory section of this article shows it nicely.

这篇关于将可选属性表示为C ++类成员的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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