下面的代码
#include <cstdint>
#include <array>
#include <utility>
std::size_t constexpr num = 5;
using Doubles = std::array<double, num>;
struct meow {
template<typename V>
static constexpr V value(V v, std::size_t)
{
return v;
}
template<typename V, std::size_t... Indices>
static constexpr auto make(V v, std::index_sequence<Indices...>) -> std::array<V, sizeof...(Indices)>
{
return {{value(v, Indices)...}};
}
Doubles doubles = make(3.1415926535897932384626433, std::make_index_sequence<num>());
};
int main()
{
meow m;
return m.doubles.size();
}
Run Code Online (Sandbox Code Playgroud)
由 GCC 以合理的方式编译,但 clang 尝试调用meow::make<double,0,1,2,3,4>而不生成实现:
https://godbolt.org/z/9Mv67GeYW
到底是怎么回事?我是否进入了IFNDR领域?
我正在使用可变参数模板,并基于这个答案写了这个:
template <size_t... I>
void print(seq<I...>)
{
decltype(std::cout) * dummy[sizeof...(I)] = { &(std::cout << I << ' ')... };
}
Run Code Online (Sandbox Code Playgroud)
因为std::cout::operator<<有一个返回类型,它可以存储,所以不需要( ,0)逗号技巧.
现在,为了关闭"未使用的变量'虚拟''警告,并打印换行符,我尝试了以下语句,但它们没有按照我的意愿行事:
dummy[0]->operator <<('\n'); // prints 10
Run Code Online (Sandbox Code Playgroud)
(显然叫做operator<<(int)代替operator<<(char)
dummy[0]->operator <<("\n"); // prints a pointer
Run Code Online (Sandbox Code Playgroud)
(显然叫做operator<<(const void*)代替operator<<(const char*)
最后,我不得不写
*dummy[0] << '\n'; // prints a newline as desired
Run Code Online (Sandbox Code Playgroud)
我的问题是,为什么选择"错误"的超载?
C++ 17 std::variant<class... Types>有一个转换构造函数
template< class T >
constexpr variant(T&& t) noexcept(/* see below */);
Run Code Online (Sandbox Code Playgroud)
(http://en.cppreference.com/w/cpp/utility/variant/variant中的第4号).它的描述是一个相当难以理解的文本墙.这是否意味着表现为变体有一堆
template< class T_i > constexpr variant(T_i&& t) noexcept;
Run Code Online (Sandbox Code Playgroud)
构造函数,类型中每个T_i一个?
我有一个具有以下签名的函数:
std::string f(const char *first, const char *last) {
std::string result;
std::for_each(first, last, some_lambda_which_appends_to_result);
return result;
}
Run Code Online (Sandbox Code Playgroud)
以及调用它的std :: string的重载:
std::string f(const std::string s) {
return f(&*s.begin(), &*s.end());
// The one below would assume that the string is not empty
// f(& s.front(), & s.front() + s.size());
}
Run Code Online (Sandbox Code Playgroud)
但是,这可能是不安全的(取消引用s.end()本身可能是一张红牌攻击).是否有一种安全的方法来获取指向字符开头的指针和一个一个接一个的结束指针(如果是空字符串,两个空指针就可以了),或者我是否必须写
std::string(const std::string& s) {
return s.empty() ? std::string() : f(& s.front(), & s.front() + s.size());
}
Run Code Online (Sandbox Code Playgroud) 我有一个与此类似的线程类:
class thr {
void run() {
for (;;) {
// block on a queue
// do some processing
++loops_;
}
}
void get_metrics(int& qps) {
std::chrono::steady_clock::time_point now = std::chrono::steady_clock::now();
double delta = std::chrono::duration<double>(now - last_metrics_time_).count();
qps = std::round(loops_ / delta);
loops_ = 0;
last_metrics_time_ = now;
}
static std::atomic<int> loops_;
static std::chrono::steady_clock::time_point last_metrics_time_;
};
std::atomic<int> thr::loops_ { 0 };
std::chrono::steady_clock::time_point thr::last_metrics_time_ {
std::chrono::steady_clock::now() // initial value: when the program starts
};
Run Code Online (Sandbox Code Playgroud)
这种运行有很多例子.还有另一个线程不时调用get_metrics().
我想阻止run()能够访问last_metrics_time_,因为它不是原子的(只有一个度量收集器线程,所以没有问题).
将last_metrics_time_ …
我有以下模板:
namespace std {
template<typename Enum>
typename std::enable_if<std::is_enum<Enum>::value, std::ostream&>::type
operator<<(std::ostream& strm, Enum e)
{
return strm << helper_of<Enum>::to_string(e);
}
}
Run Code Online (Sandbox Code Playgroud)
这有助于谷歌测试在比较霍比特人时显示人类可读的诊断:
template <typename T> struct enumclass {}; // generic template
template <typename T>
using helper_of = typename enumclass<T>::helper; // more mnemonic
namespace MiddleEarth {
enum class Hobbit { Bilbo, Frodo, Sam };
struct HobbitHelper{
std::string to_string(Hobbit H);
Hobbit from_string(std::string const& s); // Hobbit-forming
};
template <> struct enumclass<Hobbit> {
using helper = HobbitHelper; // links Hobbit to its helper
} …Run Code Online (Sandbox Code Playgroud) 以下示例代码:
#define BOOST_RESULT_OF_USE_DECLTYPE // does not help
#include <vector>
#include <algorithm>
#include <future>
#include <boost/range/algorithm.hpp>
struct DW {
std::promise<bool> success_;
};
template <class T>
class Pool
{
public:
Pool() : container_{}
{};
public:
typename std::vector<T>::iterator begin() { return container_.begin(); }
typename std::vector<T>::iterator end() { return container_.end(); }
typename std::vector<T>::const_iterator begin() const { return container_.begin(); }
typename std::vector<T>::const_iterator end() const { return container_.end(); }
private:
std::vector<T> container_; ///< holder of elements
};
#define LAMBDA [] (DW& w) { return w.success_.get_future().get(); } …Run Code Online (Sandbox Code Playgroud) 下面的代码
#include <vector>
#include <string>
template<typename T>
struct V : public std::vector<T>
{
using Impl = std::vector<T>;
using typename Impl::vector; // the constructors
};
int main()
{
std::string empty;
V<std::string> meow{42UL, empty};
}
Run Code Online (Sandbox Code Playgroud)
由 GCC 8.2 编译良好(调用size_t, string构造函数)。然而, clang up to 14 拒绝它
<source>:14:20: error: no matching constructor for initialization of 'V<std::string>' (aka 'V<basic_string<char>>')
V<std::string> meow{42UL, empty};
^ ~~~~~~~~~~~~~
<source>:5:8: note: candidate constructor (the implicit copy constructor) not viable: requires 1 argument, but 2 were provided
struct V …Run Code Online (Sandbox Code Playgroud) 这段代码
template <typename U>
struct Bar{
void setNumber(int) {}
};
template <int N>
struct Asd : public Bar<Asd<N>>{
void doSomething();
};
template<int N>
inline void Asd<N>::doSomething() {
this->template setNumber(N);
}
int main() {
Asd<42> obj;
obj.doSomething();
}
Run Code Online (Sandbox Code Playgroud)
被 GCC(甚至 13.1 和 trunk)接受,但被 clang 拒绝(https://godbolt.org/z/xbs8GqG7h)。接受它似乎是错误的(setNumber不是模板函数),所以我相信这是 GCC 中的一个错误。有人可以引用明确这一点的章节吗?
我尝试在 GCC bugzilla 中搜索“消歧器”,但只得到不相关的错误。
meow()这里第二次调用怎么编译呢?
#include <iostream>
struct F {
struct E {
using is_it_safe = bool;
};
E e;
};
template<typename T, typename = typename T::E::is_it_safe>
const void* meow(T const& t)
{
return &t;
}
int main() {
F f;
meow(f); // meow<F, bool>
meow(f.e); // meow<F::E, bool> ??
}
Run Code Online (Sandbox Code Playgroud)
F::E没有嵌套E,那么编译器如何推导第二个模板参数?
c++ ×10
c++11 ×4
templates ×2
boost ×1
c++-chrono ×1
c++14 ×1
c++17 ×1
clang ×1
compiler-bug ×1
enable-if ×1
lambda ×1
stdatomic ×1
stl ×1