Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/130.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/templates/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 为不同版本的函数模板标识不同的默认参数_C++_Templates - Fatal编程技术网

C++ 为不同版本的函数模板标识不同的默认参数

C++ 为不同版本的函数模板标识不同的默认参数,c++,templates,C++,Templates,首先我有一个函数模板 template<typename S> void foo(const S & s, int a = 1, double b = 2) 现在一切都很好 现在我想编写一个函数模板partial\u foo,它只接受一个参数double b=6,然后让编译器根据调用的foo的版本来决定a的默认参数。请注意,在foo的调用签名中,b位于a之后 输出是 foo(S) with a = 5, b = 6 foo(vector<T>) with a =

首先我有一个函数模板

template<typename S>
void foo(const S & s, int a = 1, double b = 2)
现在一切都很好

现在我想编写一个函数模板
partial\u foo
,它只接受一个参数
double b=6
,然后让编译器根据调用的
foo
的版本来决定
a
的默认参数。请注意,在
foo
的调用签名中,
b
位于
a
之后

输出是

foo(S) with a = 5, b = 6
foo(vector<T>) with a = 5, b = 6
谢谢你抽出时间

不要包含
#include
这是非标准的,在大多数平台上都不起作用

也不建议使用namespace std
,因为它可能会在将来的标准添加和您自己的代码之间产生冲突

解决问题的一种方法是将默认参数移动到具有专门功能的模板类:

#include <vector>
#include <cstdio>

using std::vector;

template <typename S>
struct defaults
{
    static constexpr int a = 1;
    static constexpr double b = 2;
};

template <typename T>
struct defaults<vector<T>>
{
    static constexpr int a = 3;
    static constexpr double b = 4;
};

template<typename S>
void foo(const S & s, int a = defaults<S>::a, double b = defaults<S>::b)
{
    printf("foo(S) with a = %d, b = %.0f\n", a, b);
}

template<typename T>
void foo(const vector<T> & t, int a = defaults<vector<T>>::a, double b = defaults<vector<T>>::b)
{
    printf("foo(vector<T>) with a = %d, b = %.0f\n", a, b);
}

template<typename S>
void foo_partial(const S & s, double b = 6)
{
    foo(s, defaults<S>::a, b);
}

int main()
{
    foo_partial(0);
    foo_partial(vector<int>());
}
#包括
#包括
使用std::vector;
模板
结构默认值
{
静态constexpr int a=1;
静态constexpr双b=2;
};
模板
结构默认值
{
静态constexpr int a=3;
静态constexpr双b=4;
};
模板
void foo(常量S&S,int a=defaults::a,double b=defaults::b)
{
printf(“a=%d,b=%.0f\n的foo”,a,b);
}
模板
void foo(常量向量&t,int a=defaults::a,double b=defaults::b)
{
printf(“a=%d,b=%.0f\n”的foo(向量),a,b);
}
模板
无效foo_部分(常数S&S,双b=6)
{
foo(s,默认值::a,b);
}
int main()
{
foo_部分(0);
foo_部分(向量());
}
如果您只是专门使用
foo
来更改默认参数,则不再需要函数重载。

不包括
#包括
,这是非标准的,在大多数平台上都不起作用

也不建议使用namespace std
,因为它可能会在将来的标准添加和您自己的代码之间产生冲突

解决问题的一种方法是将默认参数移动到具有专门功能的模板类:

#include <vector>
#include <cstdio>

using std::vector;

template <typename S>
struct defaults
{
    static constexpr int a = 1;
    static constexpr double b = 2;
};

template <typename T>
struct defaults<vector<T>>
{
    static constexpr int a = 3;
    static constexpr double b = 4;
};

template<typename S>
void foo(const S & s, int a = defaults<S>::a, double b = defaults<S>::b)
{
    printf("foo(S) with a = %d, b = %.0f\n", a, b);
}

template<typename T>
void foo(const vector<T> & t, int a = defaults<vector<T>>::a, double b = defaults<vector<T>>::b)
{
    printf("foo(vector<T>) with a = %d, b = %.0f\n", a, b);
}

template<typename S>
void foo_partial(const S & s, double b = 6)
{
    foo(s, defaults<S>::a, b);
}

int main()
{
    foo_partial(0);
    foo_partial(vector<int>());
}
#包括
#包括
使用std::vector;
模板
结构默认值
{
静态constexpr int a=1;
静态constexpr双b=2;
};
模板
结构默认值
{
静态constexpr int a=3;
静态constexpr双b=4;
};
模板
void foo(常量S&S,int a=defaults::a,double b=defaults::b)
{
printf(“a=%d,b=%.0f\n的foo”,a,b);
}
模板
void foo(常量向量&t,int a=defaults::a,double b=defaults::b)
{
printf(“a=%d,b=%.0f\n”的foo(向量),a,b);
}
模板
无效foo_部分(常数S&S,双b=6)
{
foo(s,默认值::a,b);
}
int main()
{
foo_部分(0);
foo_部分(向量());
}

如果您只是专门使用
foo
来更改默认参数,则不再需要函数重载。

您还可以使用所谓的命名参数习惯用法,这是一种更通用、更可扩展的方法:

#include <iostream>
#include <vector>

template <typename T> class Foo {
  int a_; double b_; const T& value_;
public:
  Foo(const T& value) : value_(value), a_(1), b_(2.0) { }
  Foo& set_a(int a) { a_ = a; return *this; }
  Foo& set_b(double b) { b_ = b; return *this; }
  void operator()() { std::cout << "foo(T) with a = " << a_ << " and b = " << b_ << std::endl; }
};

template <typename T> class Foo<std::vector<T>> {
  int a_; double b_; const std::vector<T>& value_;
public:
  Foo(const std::vector<T>& value) : value_(value), a_(3), b_(4.0) { }
  Foo& set_a(int a) { a_ = a; return *this; }
  Foo& set_b(double b) { b_ = b; return *this; }
  void operator()() { std::cout << "foo(std::vector<T>) with a = " << a_ << " and b = " << b_ << std::endl; }
};

template <typename T>
void foo_partial(const T& value, double b = 6) { Foo<T>(value).set_b(b)(); }

int main() {
  foo_partial(0);
  foo_partial(std::vector<int>{});
}
#包括
#包括
模板类Foo{
int a_u;双b_u;常数T和值;
公众:
Foo(const T&value):值u0(value),a 0(1),b 0(2.0){}
Foo&set_a(int a){a_=a;返回*this;}
Foo&set_b(双b){b_=b;返回*this;}

void operator(){std::cout您还可以使用所谓的命名参数习惯用法,这是一种更通用、更可扩展的方法:

#include <iostream>
#include <vector>

template <typename T> class Foo {
  int a_; double b_; const T& value_;
public:
  Foo(const T& value) : value_(value), a_(1), b_(2.0) { }
  Foo& set_a(int a) { a_ = a; return *this; }
  Foo& set_b(double b) { b_ = b; return *this; }
  void operator()() { std::cout << "foo(T) with a = " << a_ << " and b = " << b_ << std::endl; }
};

template <typename T> class Foo<std::vector<T>> {
  int a_; double b_; const std::vector<T>& value_;
public:
  Foo(const std::vector<T>& value) : value_(value), a_(3), b_(4.0) { }
  Foo& set_a(int a) { a_ = a; return *this; }
  Foo& set_b(double b) { b_ = b; return *this; }
  void operator()() { std::cout << "foo(std::vector<T>) with a = " << a_ << " and b = " << b_ << std::endl; }
};

template <typename T>
void foo_partial(const T& value, double b = 6) { Foo<T>(value).set_b(b)(); }

int main() {
  foo_partial(0);
  foo_partial(std::vector<int>{});
}
#包括
#包括
模板类Foo{
int a_u;双b_u;常数T和值;
公众:
Foo(const T&value):值u0(value),a 0(1),b 0(2.0){}
Foo&set_a(int a){a_=a;返回*this;}
Foo&set_b(双b){b_=b;返回*this;}

void operator(){std::cout谢谢,我认为这可能是一种方法!我承认我的示例中的前两行是非常糟糕的实践。谢谢你指出这一点。谢谢,我认为这可能是一种方法!我承认我的示例中的前两行是非常糟糕的实践。谢谢你指出这一点。
#include <vector>
#include <cstdio>

using std::vector;

template <typename S>
struct defaults
{
    static constexpr int a = 1;
    static constexpr double b = 2;
};

template <typename T>
struct defaults<vector<T>>
{
    static constexpr int a = 3;
    static constexpr double b = 4;
};

template<typename S>
void foo(const S & s, int a = defaults<S>::a, double b = defaults<S>::b)
{
    printf("foo(S) with a = %d, b = %.0f\n", a, b);
}

template<typename T>
void foo(const vector<T> & t, int a = defaults<vector<T>>::a, double b = defaults<vector<T>>::b)
{
    printf("foo(vector<T>) with a = %d, b = %.0f\n", a, b);
}

template<typename S>
void foo_partial(const S & s, double b = 6)
{
    foo(s, defaults<S>::a, b);
}

int main()
{
    foo_partial(0);
    foo_partial(vector<int>());
}
#include <iostream>
#include <vector>

template <typename T> class Foo {
  int a_; double b_; const T& value_;
public:
  Foo(const T& value) : value_(value), a_(1), b_(2.0) { }
  Foo& set_a(int a) { a_ = a; return *this; }
  Foo& set_b(double b) { b_ = b; return *this; }
  void operator()() { std::cout << "foo(T) with a = " << a_ << " and b = " << b_ << std::endl; }
};

template <typename T> class Foo<std::vector<T>> {
  int a_; double b_; const std::vector<T>& value_;
public:
  Foo(const std::vector<T>& value) : value_(value), a_(3), b_(4.0) { }
  Foo& set_a(int a) { a_ = a; return *this; }
  Foo& set_b(double b) { b_ = b; return *this; }
  void operator()() { std::cout << "foo(std::vector<T>) with a = " << a_ << " and b = " << b_ << std::endl; }
};

template <typename T>
void foo_partial(const T& value, double b = 6) { Foo<T>(value).set_b(b)(); }

int main() {
  foo_partial(0);
  foo_partial(std::vector<int>{});
}
foo(T) with a = 1 and b = 6    
foo(std::vector<T>) with a = 3 and b = 6