Jos*_*osh 5 c++ allocation clang
我有一个(指向)不同长度的数组的数组,我学会了我可以使用复合文字定义:
const uint8_t *const minutes[] = {
(const uint8_t[]) {END},
(const uint8_t[]) {1, 2, 3, 4, 5 END},
(const uint8_t[]) {8, 9, END},
(const uint8_t[]) {10, 11, 12, END},
...
};
Run Code Online (Sandbox Code Playgroud)
gcc接受这个很好,但是clang说:pointer is initialized by a temporary array, which will be destroyed at the end of the full-expression.这是什么意思?代码似乎正在起作用,但是当它们指向不再分配的内存时,很多东西似乎都有效.这是我需要担心的吗?(最终我只需要它与gcc一起工作.)
更新:有些可疑的事情正在发生.它在这里说:
复合文字产生左值.这意味着您可以获取复合文字的地址,该复合文字是复合文字声明的未命名对象的地址.只要复合文字没有const限定类型,就可以使用指针来修改它.
Run Code Online (Sandbox Code Playgroud)`struct POINT *p; p = &(struct POINT) {1, 1};
这个示例代码似乎正在完成我正在尝试做的事情:指向由复合文字定义的内容的指针.clang错误消息合法吗?当用clang或gcc编译时,这最终会指向未分配的内存吗?
更新2:找到一些文档:"在C中,复合文字指定一个具有静态或自动存储持续时间的未命名对象.在C++中,复合文字指定一个临时对象,它只存在于其完整表达式的末尾. "所以似乎clang是正确的警告这个,gcc可能也应该,但是,即使有-Wall -Wextra.
我无法猜测为什么从C++中删除了有用的C功能,并且没有提供完成相同功能的优雅替代方法.
嗯, clang 是对的,应该这样做:
namespace elements
{
const uint8_t row1[] = {END};
const uint8_t row2[] = {1, 2, 3, 4, 5, END};
...
}
const uint8_t *const minutes[] = {
elements::row1,
elements::row2,
...
};
Run Code Online (Sandbox Code Playgroud)
您可以想到更多 C++ 解决方案,例如使用std::tuple:
#include <tuple>
constexpr auto minutes = std::make_tuple(
std::make_tuple(),
std::make_tuple(1,2,3,4,5),
std::make_tuple(8,9,10));
#include <iostream>
#include <type_traits>
int main() {
std::cout << std::tuple_size<decltype(minutes)>::value << std::endl;
std::cout << std::tuple_size<std::remove_reference_t<decltype(std::get<1>(minutes))>>::value << std::endl;
}
Run Code Online (Sandbox Code Playgroud)