标签: variadic

可变参数扩展可以用作逗号运算符调用链吗?

我在看“如何正确使用可变参数模板的引用”,并想知道逗号扩展可以走多远。

这是答案的一个变体:

inline void inc() { }

template<typename T,typename ...Args>
inline void inc(T& t, Args& ...args) { ++t; inc(args...); }
Run Code Online (Sandbox Code Playgroud)

由于可变参数被扩展到一逗号-分隔它们的元素的列表,是那些逗号语义上等同于模板/功能参数的分离器,或者他们插入词法,使得它们适用于任何(-预处理后)的使用,包括逗号操作符?

这适用于我的 GCC-4.6:

// Use the same zero-argument "inc"

template<typename T,typename ...Args>
inline void inc(T& t, Args& ...args) { ++t, inc(args...); }
Run Code Online (Sandbox Code Playgroud)

但是当我尝试时:

// Use the same zero-argument "inc"

template<typename T,typename ...Args>
inline void inc(T& t, Args& ...args) { ++t, ++args...; }
Run Code Online (Sandbox Code Playgroud)

我不断收到解析错误,期待“;” 在“...”之前,并且“args”不会扩展其包。为什么不起作用?是因为如果“args”为空,我们会得到一个无效的标点符号?合法吗,我的编译器不够好?

(我试过在括号中围绕“args”,和/或使用后增量;都没有奏效。)

c++ variadic comma c++11

5
推荐指数
1
解决办法
1223
查看次数

使用C++ 11将可变参数函数参数转换为可变参数函数

我想将调用转发到具有可变方法的库.我能提出来复制问题的最简单的例子是:

void Bar(int useless, ...)
{
  //Does something
}

template<typename... Args>
void Foo(int useless, Args... args)
{
  Bar(useless, args...);
}
Run Code Online (Sandbox Code Playgroud)

如你所见,我已经去了.但是,即使这个编译,它似乎导致堆栈有一个摇摆,我看到应用程序退出时出错.从编译器的角度来看,我可以理解这个解决方案存在问题.

我不确定如何使这个工作,或者是否有可能让这个工作.我看到有些人建议在类似情况下使用"索引技巧",但我无法在这个特殊场合使用它.

任何帮助赞赏!

c++ templates variadic c++11

5
推荐指数
1
解决办法
1477
查看次数

带有部分参数包的Variadic辅助函数

在以下代码中:

#include <iostream>

struct Base {
    virtual ~Base() = default;
    template <typename T, typename... Args> void helper (void (T::*)(Args..., int), Args...);
    void bar (int n) {std::cout << "bar " << n << std::endl;}
};

struct Derived : Base {
    void baz (double d, int n) {std::cout << "baz " << d << ' ' << n << std::endl;}
};

template <typename T, typename... Args>
void Base::helper (void (T::*f)(Args..., int), Args... args) {
    // A bunch on lines here (hence the …
Run Code Online (Sandbox Code Playgroud)

c++ templates variadic variadic-templates c++11

5
推荐指数
3
解决办法
413
查看次数

使用可变参数模板创建哈希队列

我想使用variadic模板构建一个哈希码队列.最小的示例代码是

template<typename T>
void hash_queue(queue<size_t>& q){
  q.push( typeid(T).hash_code() );
}

template<typename T, typename... Ts>
void hash_queue(queue<size_t>& q){
  hash_queue<Ts...>(q);
  q.push( typeid(T).hash_code() );
}

int main(){
  queue<size_t> q;
  hash_queue<int, float, double>(q);
  return 0;
}
Run Code Online (Sandbox Code Playgroud)

在编译我得到

main.cpp: In instantiation of ‘void hash_queue(std::queue<long unsigned int>&) [with T = float; Ts = {double}]’:
main.cpp:19:22:   required from ‘void hash_queue(std::queue<long unsigned int>&) [with T = int; Ts = {float, double}]’
main.cpp:25:35:   required from here
main.cpp:19:22: error: call of overloaded ‘hash_queue(std::queue<long unsigned int>&)’ is ambiguous
   hash_queue<Ts...>(q);
                      ^
main.cpp:19:22: …
Run Code Online (Sandbox Code Playgroud)

c++ templates variadic variadic-templates c++11

5
推荐指数
2
解决办法
431
查看次数

如果不支持可变参数函数,Fortran中的MAX和MIN函数如何实现?

除非我弄错了,否则Fortran无法用任意数量的参数编写函数或子例程(更简洁地称为可变参数函数).

例如: RESULT = FUNC(A1, A2 [, A3 [, ...]])

我知道,我可以创建可选参数,但参数的数量是有限的,必须在函数定义中逐个手动声明.

那么Fortran编译器如何实现,MAX或者MIN实际上是

RESULT = MAX(A1, A2 [, A3 [, ...]])

特别令人困惑的是,这些可变参数MAXMIN函数显然是Fortran 77标准的一部分.因此,实现这些功能的任何能力都必须在1977年左右提供.

fortran variadic variadic-functions fortran77 fortran95

5
推荐指数
1
解决办法
5167
查看次数

在C++ 11中处理模板化函数中的void变量

我有一个模板类,必须在调用参数和返回类型为泛型的函数之前执行某些操作.

这是方法:

template <typename ReturnType, typename ...Args>
ReturnType function (Args ...args) {
  // prepare for call
  // ...
  ReturnType rv = makeCall(args...);  // [1]
  // dismiss the call
  // ...
  return rv;
}
Run Code Online (Sandbox Code Playgroud)

当然,如果ReturnType没有正确编译它void.当我在这种情况下使用它时:

function<void>(firstArg, secondArg);
Run Code Online (Sandbox Code Playgroud)

编译器响应

error: return-statement with a value, in function returning 'void' [-fpermissive]

指向标有[1]的行.

除了传递-fpermissive给编译器之外还有其他解决方案吗?我宁愿有一个独特的方法,因为我发现可能的解决方案是使用enable_if和实例化不同的版本is_same.

先感谢您.

- 更新 -

这是一个完整的例子.我应该说我们的函数确实是类方法.

#include <type_traits>
#include <iostream>

class Caller {
public:
    Caller() {}

    template <typename ReturnType, typename ...Arguments>
    ReturnType …
Run Code Online (Sandbox Code Playgroud)

c++ templates variadic c++11

5
推荐指数
2
解决办法
760
查看次数

将initializer_list转换为可变参数模板

我使用名为 fmt 的格式化库(http://fmtlib.net/latest/)。

可能的用途之一是:

fmt::format("Hello, {name}! The answer is {number}. Goodbye, {name}.", fmt::arg("name", "World"), fmt::arg("number", 42));
Run Code Online (Sandbox Code Playgroud)

我想将此调用包装在一个函数中,我将其调用为:

myFunction(myString, {"name", "World"}, {"number", 42});
Run Code Online (Sandbox Code Playgroud)

对于任意数量的参数。

到目前为止,我只成功地完成了一个可使用成对列表调用的函数:

myFunction(myString, std::make_pair("name", "World"), std::make_pair("number", 42));
Run Code Online (Sandbox Code Playgroud)

具有以下功能:

std::string myFunction(const char* str, const Args&... rest) const
{
    return fmt::format(mLocale.getPOILabel(label), fmt::arg(rest.first, rest.second)...);
}
Run Code Online (Sandbox Code Playgroud)

但我不想使用成对的。

我应该怎么办 ?

PS:fmt::arg不能在函数之间传递。

c++ variadic variadic-templates c++11 fmt

5
推荐指数
1
解决办法
691
查看次数

Python 3 类型,自定义可变参数泛型类型,具有任意数量的包含类型,怎么样?

该类typing.Tuple可以与任意数量的类型参数一起使用,例如Tuple[int, str, MyClass]Tuple[str, float]。我如何实现我自己的可以像这样使用的类?我了解如何继承typing.Generic. 下面的代码演示了这一点。

from typing import TypeVar, Generic


T = TypeVar("T")


class Thing(Generic[T]):
    def __init__(self, value: T):
        self.value = value


def f(thing: Thing[int]):
    print(thing.value)


if __name__ == '__main__':
    t = Thing("WTF")
    f(t)
Run Code Online (Sandbox Code Playgroud)

t上面的代码可以工作,但是类型检查器(在我的例子中是 PyCharm)会捕获应该是类型Thing[int]而不是 的事实Thing[str]。这一切都很好,但是如何让该类Thing支持任意数量的类型参数,就像Tuple那样?

types typing variadic python-3.x

5
推荐指数
1
解决办法
864
查看次数

如何将非可变参数值传递给 fmt::format?

我正在使用很棒的fmt C++ 库来更优雅地格式化字符串。

我想将一个非变量参数列表传递给fmt::format. 它可能是一个std::vector, 或std::string或其他任何形式,但它始终与格式字符串匹配。

所以fmt::format工作原理如下:

std::string message = fmt::format("The answer is {} so don't {}", "42", "PANIC!");
Run Code Online (Sandbox Code Playgroud)

但我想要的是这样的:

std::vector<std::string> arr;
arr.push_back("42");
arr.push_back("PANIC!");
std::string message = fmt::format("The answer is {} so don't {}", arr);
Run Code Online (Sandbox Code Playgroud)

有没有办法/解决方法来做到这一点?

c++ formatting variadic variadic-functions fmt

5
推荐指数
2
解决办法
5584
查看次数

C++:获取参数包的头和尾

如何获取参数包的前n个元素?或者最后 n 个元素,或者 [n, n+1, ..., m) 中的一片元素?例如:

head<3>(1, 2.0f, "three", '4') => make_tuple(1, 2.0f, "three")
tail<2>(1, 2.0f, "three", '4') => make_tuple("three", '4')
slice<1,3>(1, 2.0f, "three", '4') => make_tuple(2.0, "three")
Run Code Online (Sandbox Code Playgroud)

这可以通过 std::tuple、std::integer_sequence 和 std::get 的组合来实现,但我想知道是否有更简单的方法。

c++ templates variadic parameter-pack

5
推荐指数
1
解决办法
901
查看次数