我的编译器不支持make_unique.怎么写一个?
template< class T, class... Args > unique_ptr<T> make_unique( Args&&... args );
Run Code Online (Sandbox Code Playgroud) 为什么在std名称空间未定义的行为中添加名称?
显而易见的答案是"因为标准这样说",例如在C++ 14 [namespace.std] 17.6.4.2.1/1中:
如果C++程序将声明或定义添加到命名空间
std或命名空间中的命名空间std,则除非另有说明,否则C++程序的行为是未定义的....
但是,我真的对这项裁决的原因感兴趣.我当然可以理解添加已经存在的名称的重载std可能会破坏行为; 但为什么添加新的,无关的名称是一个问题?
程序已经可以在std宏内部造成严重破坏,这就是为什么几乎所有标准库实现都必须由所有非公共部分的保留名称(双下划线和起始下划线后跟资本)组成.
我真的会对这样的情况感兴趣:
namespace std
{
int foo(int i)
{ return i * 42; }
}
#include <algorithm> // or one or more other standard library headers
Run Code Online (Sandbox Code Playgroud)
当这是完全合法的,标准库必须应对:
#define foo %%
#include <algorithm> // or one or more other standard library headers
Run Code Online (Sandbox Code Playgroud)
这种未定义行为的基本原理是什么?
向std命名空间添加类型是否可以接受.例如,我想要一个TCHAR友好的字符串,以下是可接受的吗?
#include <string>
namespace std
{
typedef basic_string<TCHAR> tstring;
}
Run Code Online (Sandbox Code Playgroud)
或者我应该使用自己的命名空间?
我遇到了固定于C ++ 11功能但实现的代码库std::make_unique。namespace std如果不使用C ++ 14,则可以扩展以添加功能,即将实现包装在周围
#if defined(__cplusplus) && __cplusplus < 201402L
namespace std {
...
}
#endif
Run Code Online (Sandbox Code Playgroud)
我知道这是要扩展的未定义行为namespace std(有一些例外)。上面的情况是否仍然可以接受,还是应该避免?
我最近从Microsoft编译器切换到GCC.在很多事情中,我注意到它std::make_unique变得不可用了.这显然是因为make_unique它不是C++ 11标准的一部分,而且恰好将Microsoft作为扩展包含在内.
我们计划很快转向C++ 14,但同时我写了这个"shim"函数并将其放入std.
namespace std
{
template<typename T, typename... TArgs>
unique_ptr<T> make_unique(TArgs&&... args)
{
return std::unique_ptr<T>(new T(std::forward<TArgs>(args)...));
}
}
Run Code Online (Sandbox Code Playgroud)
这解决了gcc上的问题.但是,我认为它会在微软方面引起问题,因为它将是一个重复的定义.
有没有办法将功能正确地填充到std中,这样就不会对不同的编译器/ C++标准造成麻烦?我环顾四周,没有拿出任何东西.对于特定的标准功能,我想也许就像一个包含守卫?
#ifndef MAKE_UNIQUE_DEFINED
#define MAKE_UNIQUE_DEFINED
// Define make_unique
#endif
Run Code Online (Sandbox Code Playgroud)
可悲的是,它似乎std没有定义包含特定功能的警卫.还有什么我可以做的,以使这更正确和编译器/ C++标准不可知?
我试图为std::array类型添加我自己的构造函数,但我不确定是否可能以及如何做到这一点......
我试过这样的事:
typedef unsigned char byte_t;
namespace std {
template<std::size_t _Nm>
array::array(std::vector<byte_t> data)
{
// Some content
}
}
Run Code Online (Sandbox Code Playgroud)
我想创建一个非常简单的机制来转换std::vector<byte_t>到std::array<byte_t, size>.
我正在使用C++ 14(我不能在我的项目中使用更新的标准)
写了我自己的数字类。超载std::numeric_limit::max()就好。然而,我正在尝试超载std::abs()但编译器不喜欢我的尝试。我试过这个:
namespace std \n{\n template<uint8_t T> \n MyType<T> abs(const MyType<T>& mt)\n {\n MyType<T> copy = mt;\n copy.val = std::abs(md.val);\n return copy;\n }\n}\nRun Code Online (Sandbox Code Playgroud)\n但是,编译器没有发现重载:
\nerror: no matching function for call to \xe2\x80\x98abs(const MyType<10>&)\xe2\x80\x99\n/usr/include/c++/11/bits/std_abs.h:56:3: note: candidate: \xe2\x80\x98long int std::abs(long int)\xe2\x80\x99\n 56 | abs(long __i) { return __builtin_labs(__i); }\n | ^~~\n/usr/include/c++/11/bits/std_abs.h:56:12: note: no known conversion for argument 1 from \xe2\x80\x98const MyType<10>\xe2\x80\x99 to \xe2\x80\x98long int\xe2\x80\x99\n 56 | abs(long __i) { return __builtin_labs(__i); }\n | ~~~~~^~~\n/usr/include/c++/11/bits/std_abs.h:61:3: note: candidate: …Run Code Online (Sandbox Code Playgroud) c++ ×7
c++14 ×3
c++11 ×2
c++20 ×1
namespaces ×1
std ×1
stdarray ×1
stdvector ×1
stl ×1
unique-ptr ×1