C++在给类变量赋值时使用花括号的方法

3
当我在C++中声明数组时,可以像这样使用花括号:
int var[3] = {1, 2, 3};

我能在类中使用花括号声明,就像运算符重载一样吗?我的意思是这样的:

class example
{
private:
    int m_sum;
public:
    void operator{}(int a, int b, int c)
    {
        m_sum = a+b+c;
    }
    int get_sum()
    {
        return m_sum;
    }
}

int main()
{
    example ex = {1, 2, 3};
    std::cout << ex.get_sum() << endl; // prints 6
    return 0;
}

上面的代码只是我的想象,但我想使用花括号来表示这段代码。

2
为什么不使用 example ex(1,2,3) - user707650
@Evert 因为我想在声明类变量时获取可变参数。使用 stdarg.h 可能是一个不错的选择,但它需要一个包含参数数量的参数。花括号赋值不需要它,至少当我声明纯 C 数组时。 - Mossid
@quantdev 谢谢!我现在不太确定,但也许这正是我想要的。 - Mossid
1
也许你需要一个可变参数构造函数模板。class example { template <class... Ts> example(Ts&&... vs); }; 只有当所有参数具有相同的类型时,初始化列表才起作用。 - Oktalist
@Oktalist 看起来非常有用。谢谢你。 - Mossid
2个回答

10
你可能需要一个接受 std::initializer_list 的构造函数:
#include <iostream>
#include <algorithm>
#include <initializer_list>

class example
{
private:
    int m_sum;
public:
    example(std::initializer_list<int> parameters)
    {
        m_sum = std::accumulate(std::begin(parameters), std::end(parameters), 0);
    }

    int get_sum() const
    {
        return m_sum;
    }
};

int main() {
    example e = { 1, 2, 3, 4 };
    std::cout << e.get_sum();
}

实时演示


另一个方法是使用变参模板构造函数(我认为它不太易读,但它的优点在于使您的代码通用:您可以将任意元素传递给构造函数):

#include <iostream>
#include <algorithm>
#include <initializer_list>

class example
{
private:
    int m_sum;
public:
    template <class... Ts> example(Ts&&... vs) : m_sum(compute_sum(vs...)) { }

    int get_sum() const
    {
        return m_sum;
    }

private:
    template<typename Ts1>
    Ts1 compute_sum(const Ts1& val) { return val; } // termination

    template<typename Ts1, typename... Ts>
    Ts1 compute_sum(const Ts1& arg1, const Ts&... args)
    {
        return arg1 + compute_sum(args...); 
    }
};

演示页面


注意:

C++ 中不存在 operator{} 这个运算符。


我尝试在您的第一个代码示例中传递一个数组,但它没有起作用。有没有办法将整数数组传递给构造函数? - Superman
@Superman:你不能使用初始化列表完成这个动作,它们只能在列表初始化时作为数组的代理。但你可以添加一个构造函数让它适用于任何容器,包括数组,请参见这里 - quantdev

3
如果您可以使用现代的C++(例如C++11),则可以使用std::initializer_list。大多数现代编译器都支持它,只需添加-std=c++11编译标志即可。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接