当声明/参数相同时,如何重载构造函数/函数?[关闭]

How to overload constructors/functions when declarations/parameters are the same? [closed]

提问人:zonn 提问时间:5/29/2017 最后编辑:zonn 更新时间:5/29/2017 访问量:271

问:


想改进这个问题吗?通过编辑这篇文章添加详细信息并澄清问题。

6年前关闭。

我想创建一个类来管理矩阵,但我遇到了构造函数的问题。 目的是找到调用 Matrix 对象的构造函数的最短方法,因为要知道某些构造函数具有相同的标头以保持清晰。 这是我试图得到的想法:

Matrix id; // create identity matrix
Matrix scale(x, y, z); // create directly a scale matrix
Matrix translation(x, y, z) // create a translation matrix
...

在这里,所有参数都是 s,所以我无法重载构造函数,我唯一看到的就是使用模板,但仅限于那些特殊情况,然后我不知道该怎么做。float

溶液

最后,我决定做一个这样的抽象类:

class _Mat
{
    public :
        virtual ~_Mat(void) = 0;

        // ...
}

class Mat : public _Mat
{
    public :
        Mat(void);
        virtual ~Mat(void);

        class Scale : public _Mat
        {
            public :
                Scale(float x, float y, float z);
                vitual ~Scale(void);

                // ...
        }

        // ...
}

所有这些都将被定义到,而另一个类将只对它们的构造函数有用_Mat

最后,我们可以像这样调用构造函数:

Mat id;
Mat::Scale scale(2, 2, 2);
// ...
C++ 构造函数-重载

评论

0赞 Michael Albers 5/29/2017
听起来你应该看看继承。
1赞 zonn 5/29/2017
但是类是相同的,只是构造函数发生了变化,例如创建“MatrixScale”很奇怪,它与“Matrix”相同,只是构造函数不同
0赞 Logman 5/29/2017
请澄清您的问题,因为它不清楚您想要什么。 并且是不同的类型,这里没有发生过载。Matrix<Scale>Matrix<Translation>
1赞 Logman 5/29/2017
好的,现在很清楚你想要什么了。但是你完全误解了constrictor的概念。构造函数是一种创建类 Matrix 而不是 Scale 或 Translation 的方法。如果要创建 Scale(或连接到 Matrix 的任何其他对象),这里有多个选项。其中一些是迈克·纳基斯(Mike Nakis)在他的回答中发布的。如果你不需要动态创建矩阵,我也会选择构建器方法,如 HolyBlackCat 在他的回答中所示。

答:

2赞 Mike Nakis 5/29/2017 #1

您有以下选择:

  1. 在构造函数中引入不同类型的不同虚拟参数,以区分重载。这很笨拙,我不推荐它。

  2. 使用继承。创建不同的子类,其中每个子类都以其构造函数提供的功能命名。

  3. 将构造函数设为私有,并引入具有漂亮且长名称的工厂方法,这些名称清楚地指示它们的作用。 (无重载。public static

就个人而言,我会选择第三种选择。

4赞 Quentin 5/29/2017 #2

您正在寻找标签调度。您可以在标准库中看到它,例如在 std::p air 构造函数的重载中。

你只需要声明一个 “tag” 结构,用于指导重载解决:

struct translation_matrix_tag_t {} static translation_matrix_tag;
struct scale_matrix_tag_t {} static scale_matrix_tag;

然后重载你的构造函数:

struct Matrix {

    Matrix(translation_matrix_tag_t, float, float, float);
    Matrix(scale_matrix_tag_t, float, float, float);

    // ...
};

然后你可以像这样使用它:

void foo() {
    Matrix m1{translation_matrix_tag, x, y, z};
    Matrix m2{scale_matrix_tag, x, y, z};
}

评论

0赞 zonn 5/29/2017
但是我们发送一个新参数只是为了指定我们想要与此解决方案一起使用的内容,不是吗?
0赞 Quentin 5/29/2017
@Zone31是的,这就是我们所做的。
0赞 zonn 5/29/2017
没有办法在不为构造函数的主体添加无用参数的情况下调用构造函数?
1赞 Quentin 5/29/2017
@Zone31它包含与其他参数一样多的信息,即应该如何解释它们。但是,如果这真的让你感到恼火,你可以改用工厂函数。他们也很好。
4赞 HolyBlackCat 5/29/2017 #3

您可以保持简单并使用静态成员函数:

struct Matrix
{
    // ...

    static Matrix Translate(float x, float y, float z) {/*...*/}
    static Matrix Scale(float x, float y, float z) {/*...*/}
};

// ...

Matrix m = Matrix::Scale(1,2,3);

评论

0赞 zonn 5/29/2017
谢谢,你给了我一个参考运算符的想法