将指针设置为一个值加上一个单独的值

Set pointer to a value plus a separate value

本文关键字:一个 上一个 单独 设置 指针      更新时间:2023-10-16

是否可以将指针设置为一个值,但有一点偏移。

类似于:

m_NewPosition = &m_Position + Vector3(0,0,10);

因此,NewPosition的值是实际位置加上前面的10。

使用c++。

只有当指针指向数组时,才能将偏移量与指针一起使用。

因此,如果你有char arr[10];,并且你用一些东西填充它,那么你可以做char *p = arr + calc_offset();,前提是你不超出数组的边界。

来自C++标准:

如果指针操作数和结果都指向相同的数组对象或经过数组对象的最后一个元素的一个数组对象,评估不应产生过度流动;否则,行为未确定。

是的,您可以对指针执行arichematic,但除非新指向的地址指向有效的取消引用,否则将导致UB。

您想要获取m_Position的地址并向其添加向量似乎很奇怪。如果我们知道您的指针在哪里,也许会对我们有更多帮助。我们不知道m_NewPositionm_Position的类型,所以很难提供帮助。然而,你似乎不太可能在这里需要指针。

我假设这两个变量的类型是Position,这是一个类似于的类

class Position {
 public:
  Position(int x, int y, int z) : x(x), y(y), z(z) { }
 private:
  int x;
  int y;
  int z;
}

如果是这种情况,并且您希望将Vector3作为第二个操作数应用于此位置,则需要重载此类上的operator+。要做到这一点,可以这样做:

class Position {
 public:
  Position(int x, int y, int z) : x(x), y(y), z(z) { }
  Position operator+(const Vector3& vector) {
    return Position(x + vector.x, y + vector.y, z + vector.z);
  }
 private:
  int x;
  int y;
  int z;
}

如您所见,operator+方法允许您将矢量添加到此位置。现在你只需要做:

m_NewPosition = m_Position + Vector3(0,0,10);

然而,在本例中,m_Position不会更改。它将保持原来的位置。对operator+的调用将只返回一个具有更新组件的新Position。如果要更新m_Position,则可能需要重载operator+=

听起来您实际要查找的是一个函数,其结果随m_Position的值而变化。根据m_前缀,我认为他们都是成员。如果m_Position + Vector3(0,0,10)是常数,它可能只是一个正常的成员函数:

Vector3 m_NewPosition() const {
    return m_Position + Vector(0,0,10);
}

但是,如果你想改变功能,那么你可以使用std::function<Vector3(void)>,并像这样分配:

m_NewPosition = [&m_Position]() { return m_Position + Vector3(0,0,10); };

这里有一个简单的例子,但使用了整数而不是矢量。

#include <iostream>
#include <functional>
struct Foo
{
    Foo()
        :X(0)
    {
        NewX = [&X]() { return X + 10; };
    }
    int X;
    std::function<int(void)> NewX;
};
int main()
{
    Foo f;
    for (f.X=0; f.X<10; ++f.X)
    {
        std::cout << f.NewX() << 'n';
    }
}

还有一个在线演示,这样你就可以查看它的输出:http://ideone.com/XTwE7


另一种选择是确保m_Position和m_NewPosition都是私有的,并且永远不要直接修改它们,而只能通过访问器功能进行修改,例如

class Foo
{
public:
    void IncrementPosition(const Vector3 & rhs)
    {
        m_Position += rhs;
        m_NewPosition = m_Position + Vector3(0,0,10);
    }
private:
    Vector3 m_Position, m_NewPosition;
};

如果我理解正确,您希望m_NewPosition在任何时候都等于m_Position加上一些空间偏移,即使它被修改(类似于反应式编程)。这是不可能实现的方式,你试图做到这一点,你可能应该找到一些很好的参考指针。但是,您有一些解决方案可供选择。

第一种是使用函数/方法,就像@Benjamin Lindley提出的那样:由于NewPosition是一个计算值,因此在函数中计算它是有意义的:

class Character
{
  public:
    Vector3 getPosition() const
    {
        return m_Position;
    }
    Vector3 getNewPosition() const
    {
        return getPosition() + Vector3(0, 0, 10);
    }
  private:
    Vector3 m_Position;
};

这就是封装的全部要点,意味着隐藏对象的内部:对象的"可见"属性应该只能通过成员函数(方法)访问,允许您更改它们的存储方式或动态计算它们,就像您的示例中的m_NewPosition一样。

另一个更复杂的解决方案(在您的情况下可能不合适)是编写一个表示相对位置的新类:

class RelativePosition
{
  public:
    RelativePosition(Vector3 const & origin, Vector3 const & offset)
      : m_Origin(origin), m_Offset(offset)
    {}
    Vector3 getAbsolutePosition() const
    {
        return m_Origin + m_Offset;
    }
  private:
    Vector3 const & m_Origin;
    Vector3 m_offset;
};

注意RelativePosition是如何存储对其来源的引用而不是副本的;正因为如此,如果原点被修改(即移动),相对位置将反映这种变化。

现在,您可以使用此类的实例来表示m_newPosition,它实际上是一个相对位置(相对于m_Position,偏移量为`Vector3(0,0,10))。然而,正如我之前所说的,我认为这个解决方案可能对您的情况来说有些过头了;你可能应该坚持以前的方法。