如何通过派生类函数从基类更改向量
Posted
技术标签:
【中文标题】如何通过派生类函数从基类更改向量【英文标题】:How to change the a vector from a base class via a derived class function 【发布时间】:2020-02-25 06:55:53 【问题描述】:我创建了一个名为 Shape_2D 的基类,它将被所有形状类继承
Shape_2D.h
private:
std::vector<Point> points_within_shape_;
std::vector<Point> points_on_perimeter_;
public:
std::vector<Point> get_Points_Within_Shape();
std::vector<Point> get_Points_On_Perimeter();
Shape_2D 类只有 1 个构造函数 Shape_2D.cpp
Shape_2D::Shape_2D(const std::string &name, const bool &contain_Warp_Space)
: name_(name), contain_warp_space_(contain_Warp_Space)
std::vector<Point> Shape_2D::get_Points_Within_Shape()
return this->points_within_shape_;
std::vector<Point> Shape_2D::get_Points_On_Perimeter()
return this->points_on_perimeter_;
鉴于上面的代码,我想获取一个形状(在本例中为矩形)内的所有点,并让它返回所有点的向量。
该功能针对每个形状单独实现 这个例子是矩形类
矩形.h
std::vector<Point> get_All_Point_In_Shape() override;
std::vector<Point> get_All_Point_On_Shape() override;
在 Rectangle 的构造函数中,我立即尝试使用下面定义的函数来分配向量。
矩形.cpp
Rectangle::Rectangle(const std::array<Point, 4> &vertices, const bool &warp_space)
: Shape_2D("Rectangle", warp_space), vertices_(vertices), area_(compute_Area())
get_Points_Within_Shape() = get_All_Point_In_Shape();
get_Points_On_Perimeter() = get_All_Point_On_Shape();
std::vector<Point> Rectangle::get_All_Point_In_Shape()
std::vector<Point> points_within_shape;
for (int x = vertices_[0].get_X() + 1; x < vertices_[2].get_X(); x++)
for (int y = vertices_[1].get_Y() + 1; y < vertices_[0].get_Y(); y++)
if (is_Point_In_Shape(x, y))
points_within_shape.push_back(Point(x, y));
return points_within_shape;
std::vector<Point> Rectangle::get_All_Point_On_Shape()
std::vector<Point> points_on_perimeter;
for (int x = vertices_[0].get_X(); x <= vertices_[2].get_X(); x++)
for (int y = vertices_[1].get_Y(); y <= vertices_[0].get_Y(); y++)
if (is_Point_On_Shape(x, y))
points_on_perimeter.push_back(Point(x, y));
return points_on_perimeter;
然而,当我通过调试器运行它们时,我发现尽管函数工作正常,但在 Shape_2D 中声明的向量不会相应地更新。我可以做些什么来解决这个问题吗?
【问题讨论】:
要么使成员变量protected
或在基类中提供protected
函数修改。 protected
是private
和public
之间的中间体,它只扩展了对派生类的访问。 (当然,friend
是另一种选择,但可能不适合您的具体情况。)
你好约苏阿。请提供一些反馈,您是否设法解决了您的问题?给出的答案有帮助吗?如果是,请考虑投票并将其标记为已接受。
【参考方案1】:
您的问题是您将函数 get_Points_Within_Shape()
和 get_Points_On_Perimeter()
定义为返回内部向量的副本。相反,您应该定义它们以将 references 返回到内部向量。此外,此类函数通常有 2 个版本:通常函数返回普通向量和 const
函数返回 const
向量。 IE。您的声明应如下所示:
std::vector<Point>& get_Points_Within_Shape() return points_within_shape_;
const std::vector<Point>& get_Points_Within_Shape() const return points_within_shape_;
【讨论】:
【参考方案2】:问题是 get_Points_Within_Shape
和 get_Points_On_Perimeter
方法正在返回点向量的副本,因此您基本上只需分配给该副本,然后在语句执行完成后将其销毁(因为它没有保存到一个变量)。
您的选择是使 points_within_shape_
和 points_on_perimeter_
受保护,以便派生类可以访问它们(如 cmets 中建议的那样),或者为允许修改数据的 getter 函数提供重载:
std::vector<Point> &get_Points_Within_Shape()
return points_within_shape_;
const std::vector<Point> &get_Points_Within_Shape() const
return points_within_shape_;
请注意,第一个方法提供了访问数据的能力,因为它返回一个非常量引用。另一种选择是在基类中实现一个 setter:
void set_Points_Within_Shape(const std::vector<Point> &points)
points_within_shape_ = points;
即使您决定使用 setter,您仍应更改您的 getter 类以返回 const std::vector<Point> &
。这样,您不会在每次要读取它们时将所有点复制到一个新向量中。如果向量中有很多点,这可能是主要的性能损失。
附:
虽然这是最简单的方法,但请避免将派生类声明为friend
。这应该只在某些特定情况下使用,绝对不能在一个类从另一个类继承的情况下使用。
【讨论】:
以上是关于如何通过派生类函数从基类更改向量的主要内容,如果未能解决你的问题,请参考以下文章