我怎么能写一个函数,接受可变数量的参数?这可能吗?怎么可能?
当前回答
// spawn: allocate and initialize (a simple function)
template<typename T>
T * spawn(size_t n, ...){
T * arr = new T[n];
va_list ap;
va_start(ap, n);
for (size_t i = 0; i < n; i++)
T[i] = va_arg(ap,T);
return arr;
}
用户写道:
auto arr = spawn<float> (3, 0.1,0.2,0.3);
从语义上讲,这看起来和感觉上完全像一个n参数函数。在引擎盖下,你可能会以这样或那样的方式打开它。
其他回答
c++支持C风格的变进函数。
然而,大多数c++库使用另一种习惯,例如,' C ' printf函数接受变量参数,而c++ cout对象使用<<重载来解决类型安全和adt(可能以实现简单性为代价)。
支持彩色代码的c++ 11
是通用的,适用于所有数据类型 类似JavaScript console.log(1,"23") 支持颜色代码的信息,警告,错误。 例子:
#pragma once
#include <iostream>
#include <string>
const std::string RED = "\e[0;91m";
const std::string BLUE = "\e[0;96m";
const std::string YELLOW = "\e[0;93m";
class Logger {
private:
enum class Severity { INFO, WARN, ERROR };
static void print_colored(const char *log, Severity severity) {
const char *color_code = nullptr;
switch (severity) {
case Severity::INFO:
color_code = BLUE.c_str();
break;
case Severity::WARN:
color_code = YELLOW.c_str();
break;
case Severity::ERROR:
color_code = RED.c_str();
break;
}
std::cout << "\033" << color_code << log << "\033[0m -- ";
}
template <class Args> static void print_args(Args args) {
std::cout << args << " ";
}
public:
template <class... Args> static void info(Args &&...args) {
print_colored("[INFO] ", Severity::INFO);
int dummy[] = {0, ((void)print_args(std::forward<Args>(args)), 0)...};
std::cout << std::endl;
}
template <class... Args> static void warn(Args &&...args) {
print_colored("[WARN] ", Severity::WARN);
int dummy[] = {0, ((void)print_args(std::forward<Args>(args)), 0)...};
std::cout << std::endl;
}
template <class... Args> static void error(Args &&...args) {
print_colored("[ERROR]", Severity::ERROR);
int dummy[] = {0, ((void)print_args(std::forward<Args>(args)), 0)...};
std::cout << std::endl;
}
};
使用可变模板,示例重现console.log,如JavaScript所示:
Console console;
console.log("bunch", "of", "arguments");
console.warn("or some numbers:", 1, 2, 3);
console.error("just a prank", "bro");
文件名,例如js_console.h:
#include <iostream>
#include <utility>
class Console {
protected:
template <typename T>
void log_argument(T t) {
std::cout << t << " ";
}
public:
template <typename... Args>
void log(Args&&... args) {
int dummy[] = { 0, ((void) log_argument(std::forward<Args>(args)),0)... };
cout << endl;
}
template <typename... Args>
void warn(Args&&... args) {
cout << "WARNING: ";
int dummy[] = { 0, ((void) log_argument(std::forward<Args>(args)),0)... };
cout << endl;
}
template <typename... Args>
void error(Args&&... args) {
cout << "ERROR: ";
int dummy[] = { 0, ((void) log_argument(std::forward<Args>(args)),0)... };
cout << endl;
}
};
如果不使用C风格的可变参数(…),就没有标准的c++方法可以做到这一点。
当然,根据上下文,有一些默认参数“看起来”像可变数量的参数:
void myfunc( int i = 0, int j = 1, int k = 2 );
// other code...
myfunc();
myfunc( 2 );
myfunc( 2, 1 );
myfunc( 2, 1, 0 );
这四个函数调用都使用不同数量的参数调用myfunc。如果没有给出参数,则使用默认参数。但是请注意,只能省略尾随参数。没有办法,例如省略i而只给出j。
在c++11中,你可以做:
void foo(const std::list<std::string> & myArguments) {
//do whatever you want, with all the convenience of lists
}
foo({"arg1","arg2"});
列表初始化项FTW!