标签: static-assert

constexpr std :: array with static_assert

#include <iostream>
#include <array>

int main(int argc, char **argv) {
    constexpr const std::array<int, 2> arr {{ 0, 1 }};
    constexpr const int arr2[] = { 0, 1};

    static_assert(arr[0] == arr2[0], "asdf");
    static_assert(arr[1] == arr2[1], "asdfasdf");

    return 0;
}
Run Code Online (Sandbox Code Playgroud)

当编译gcc 4.8.24.9.1使用g++ test.cpp --std=c++11,编译成功.当编译clang 3.43.5利用clang++ test.cpp --std=c++11然而,编译失败:

test.cpp:8:16: error: static_assert expression is not an integral constant expression
        static_assert(arr[0] == arr2[0], "asdf");
                      ^~~~~~~~~~~~~~~~~
test.cpp:8:16: note: non-constexpr function 'operator[]' cannot be used …
Run Code Online (Sandbox Code Playgroud)

c++ static-assert constexpr c++11 stdarray

10
推荐指数
1
解决办法
1228
查看次数

未定义的行为会影响static_assert吗?

考虑以下代码:

SomeType x=getX();
for(auto mask = 1u<<(CHAR_BIT*sizeof x - 1);/*...*/;/*...*/)
{
    static_assert(sizeof mask>=sizeof x, "Type of numeric parameter is too long");
    /*...*/
}
Run Code Online (Sandbox Code Playgroud)

在这里,mask将具有type unsigned。假设SomeTypelong long。然后,mask由于移动过多,初始化会具有不确定的行为。但是OTOH中有一个static_assert,用于检查在运行时不会发生未定义的行为(因为代码将无法编译)。

但是,由于UB可能导致时间悖论和其他意外事件,因此我不确定static_assert在这种情况下是否可以保证它确实有效。有什么理由可以确定吗?还是应该static_assert在初始化之前重做此代码mask

c++ static-assert undefined-behavior

10
推荐指数
1
解决办法
145
查看次数

static_assert()的优雅方式是订购标准库容器类型?

在模板化函数中,其中一个参数是类型的标准库容器T,我可以轻松地静态断言这T是一个有序容器吗?

有没有更优雅的方式来做这个比做类型特定的事情,比如测试一个hash_function()功能的存在来区分std::mapstd::unordered_map

c++ templates stl static-assert c++11

9
推荐指数
1
解决办法
1248
查看次数

在Swift中编译时间断言?

是否可以像在C++中的static_assert一样在Swift中编译一个编译时断言?也许某种方式利用泛型的类型约束来强制编译器中断?

assert static-assert swift

9
推荐指数
1
解决办法
1970
查看次数

static断言模板typename T不完整?

有没有办法在标题中的那个点上使用static_assert类型T 完整?如果有人在他们不应该的地方添加#includes,那么这个想法就会产生编译错误.

相关: 如何写`is_complete`模板?

使用该链接的答案,

namespace
{
template<class T, int discriminator>
struct is_complete {
  static T & getT();
  static char (& pass(T))[2];
  static char pass(...);
  static const bool value = sizeof(pass(getT()))==2;
};
}
#define IS_COMPLETE(X) is_complete<X,__COUNTER__>::value
class GType;
static_assert(!IS_COMPLETE(GType),"no cheating!");
Run Code Online (Sandbox Code Playgroud)

不幸的是,这给出了"无效使用incomlete类型"错误,哦.有没有办法断言否定?

c++ templates static-assert incomplete-type

9
推荐指数
1
解决办法
803
查看次数

如何在C++中打印编译时计算的结果?

我写了几个constexpr函数,并在static_asserts中使用它们来控制一些资源限制.但是我不仅要强制执行编译时谓词,还要查看在正常编译过程中计算的实际值,或者至少在断言失败时.

有很多方法可以在编译期间打印字符串消息,但是打印constexpr计算的结果是什么?

c++ gcc static-assert constexpr c++11

9
推荐指数
2
解决办法
2603
查看次数

当通过decltype表达式调用时,static_assert是否可以工作?

我希望以下代码失败并static_assert检查最后一行.但是在MSVC2015和gcc 6.2中,它成功编译.它确实无法在clang 3.9中按预期编译.这是编译器错误还是static_assert内部不起作用decltype()

#include <tuple>
#include <type_traits>

template<typename T>
struct Wrapper {};

template<typename T, typename U>
constexpr std::tuple<T, U> operator|(Wrapper<T>, Wrapper<U>)
{
    static_assert(std::is_same<T,U>::value == false, "can't combine two of the same type");
    return std::tuple<T, U> {};
}

struct A {};
struct B {};
constexpr Wrapper<A> aaa = {};
constexpr Wrapper<B> bbb = {};

constexpr auto shouldPass1 = aaa | bbb;
//constexpr auto shouldFail1 = aaa | aaa; // fails static assert as expected
using …
Run Code Online (Sandbox Code Playgroud)

c++ static-assert decltype c++11

9
推荐指数
1
解决办法
413
查看次数

是否允许编译器评估静态断言中的重言式

提供static_assert模板通常很有帮助.在模板不应该以某种方式实例化的情况下,我经常这样做

template<typename T, typename = void>
struct S
{
    static_assert(false, "Unconditional error");
    static_assert(sizeof(T) != sizeof(T), "Error on instantiation");
};

template<typename T>
struct S<T, std::enable_if_t<std::is_integral_v<T>>>
{
    // ...
};
Run Code Online (Sandbox Code Playgroud)

static_assert即使没有实例化,第一个将立即失败S,而如果没有实例化将导致主模板,第二个将成功.

第二个static_assert显然是一个重言式,但它"取决于" T,以达到预期的效果.但这有保证吗?是否允许编译器评估这些重言式?

c++ static-assert language-lawyer

9
推荐指数
1
解决办法
200
查看次数

约束允许在函数参数上使用static_assert吗?

当前,即使对它的所有调用确实为,也无法用于static_assert验证constexpr函数的参数constexpr。这是有道理的,因为在某些其他模块尝试调用该函数的情况下,编译器仍必须为此函数创建一个非constexpr实例。可悲的是,即使函数是static或位于匿名名称空间中,也是如此。

然而,C ++ 20将引入一个新的关键字consteval,类似于constexpr但不允许以非constexpr的方式调用函数。在这种情况下,编译器可以确定在编译时始终知道函数参数。因此,从理论上讲,应该有可能使用进行验证static_assert

问题是:标准允许吗?


例:

#include <iostream>

consteval char operator""_bchar(const char text[], const size_t length)
{
    static_assert(length == 8, "Binary char has to have 8 digits!"); // <-- This is currently not possible.
    uint8_t byte = 0;
    for (size_t i = 0; i != length; ++i)
    {
        byte <<= 1;
        byte |= text[i] == '1' ? 0b00000001 : 0b00000000;
    }
    return byte;
}

int main() …
Run Code Online (Sandbox Code Playgroud)

c++ static-assert c++20 consteval

9
推荐指数
1
解决办法
254
查看次数

如果在 constexpr 上下文中,如何在 assert() 和 static_assert()、dependend 之间分派?

在 C++11 constexpr 函数中,assert()不可能使用第二个语句,例如 an 。Astatic_assert()很好,但如果该函数被称为“正常”函数,则它不起作用。逗号运算符可以来帮助wrto。的assert(),而是丑陋和一些工具吐出它的警告。

考虑这样的“getter”,它在断言旁边是完全可构造的。但是我想为运行时和编译时保留某种断言,但不能仅根据“constexpr”上下文进行重载。

template<int Size>
struct Array {
  int m_vals[Size];
  constexpr const int& getElement( int idx ) const
  {
    ASSERT( idx < Size ); // a no-go for constexpr funcs in c++11
    // not possible, even in constexpr calls as being pointed out, but what I would like:
    static_assert( idx < Size, "out-of-bounds" );
    return m_vals[idx];
  }
};
Run Code Online (Sandbox Code Playgroud)

附带条件:C++11,无堆,无异常,无编译器细节。

注意正如评论者指出的那样(谢谢!),static_assert论点是不可能的(但会很好)。在这种情况下,编译器在越界访问时给了我一个不同的错误。

c++ assert static-assert constexpr c++11

9
推荐指数
1
解决办法
330
查看次数