c++ 参数未传递到运算符重载中<

c++ Parameters not passed into operator overload<

本文关键字:重载 lt 运算符 参数 c++      更新时间:2023-10-16

为类"State"创建运算符重载时,我重载的运算符没有初始化任何成员变量。

    bool operator<(const State m)const  
    {
       return (mDist < m.mDist);
    }

将状态添加到调用此运算符的优先级队列时,不会初始化 mDist 的值

这是开始该过程的代码

int row=0;
int col=0;
current.getBlank(row, col); // gets position of 0 in 3x3 int array

if (row > 0)
{   
    //creates a new state with current 3x3 array and postion of 0 as member variables
    State u(current, row, col); 
    u.swapUp();           // swaps 0 with position above it
    //n.findMDist(goal);  //calculates Manhattan distance from goal state
    nextMoves.push(u);    //push into queue
}

关于我应该检查哪些可能导致值传递给运算符重载的任何建议?

编辑:

这是我的州级。

#pragma once
#ifndef STATE_H_
#define STATE_H_
#include<iostream>
#include <vector>
using namespace std;
const int SIZE = 3;
class State
{
private:
    int board[SIZE][SIZE];
    int blankRow;
    int blankCol;
    State *parent;
    State *goal;
public:
    State() 
    {
        int counter = 0;
        for (int i = 0; i < SIZE; i++)
            for (int j = 0; j < SIZE; j++)
            {
                setValue(i, j, counter);
                counter++;
            }
        int mDist = 0;
    }
    State(const State& s) 
    {
        for (int i = 0; i < SIZE; i++)
            for (int j = 0; j < SIZE; j++)
                board[i][j] = s.getValue(i, j);
    }
    State(const State& s, int r, int c, State *g) 
    {
        for (int i = 0; i < SIZE; i++)
            for (int j = 0; j < SIZE; j++)
                board[i][j] = s.getValue(i, j);
        blankRow = r;
        blankCol = c;
        goal = g;
        findMDist(*goal);
    }
    //get
    int mDist;

    //find
    void findMDist(State Goal);

    bool operator<( State m)const   
    {
        return (mDist < m.mDist);
    }
};
#endif

这是实现 mDist 的地方

void Game::next() {
int row=0;
int col=0;
current.getBlank(row, col);

if (row > 0)
{
    State u(current, row, col);
    u.swapUp();
    n.findMDist(goal);
    nextMoves.push(u);
}
if (row < 2)
{
    State d(current, row, col);
    d.swapDown();
    n.findMDist(goal);
    nextMoves.push(d);
}
if (col < 2)
{
    State n(current, row, col);
    n.swapRight();
    n.findMDist(goal);
    nextMoves.push(n);
}
if (col > 0)
{
    State n(current, row, col);
    n.swapLeft();
    n.findMDist(goal);
    nextMoves.push(n);
}
}
bool operator<( State m)const

这将按值传递,因此调用复制构造函数。这是:

State(const State& s)
{
    for (int i = 0; i < SIZE; i++)
        for (int j = 0; j < SIZE; j++)
            board[i][j] = s.getValue(i, j);
}

这仅复制board。它完全省略了通过复制所有其他成员变量(包括有问题的mDist(来正确完成其工作。

因此,operator<最终处理一个不完整的副本,其中多个成员变量未初始化,因此您可以通过随后读取它们来调用未定义的行为。

修复程序包括:

  • 实现一个完成其工作的适当复制构造函数,即复制所有成员变量,并在完成后导致所有外部可见状态相同。
  • 但是,不要将值传递给复制构造函数,因为这会浪费资源和糟糕的语义。而是经过const&

关于我应该检查可能导致值 mot 的任何建议 传递给操作员超载?

当您将State的副本传递给您时 operator< ,不会复制mDist。您可以将mDist = s.mDist;添加到复制构造函数中(实际上您可能无论如何都想添加它(,但最好通过 const ref 将State传递给比较器:

bool operator<(State const &m) const   
{
    return (mDist < m.mDist);
}

同样在你的构造函数中,你有局部变量初始化int mDist = 0;这是没有意义的,因为它几乎立即超出了范围。我想你的意思是mDist = 0;这将照顾你目前未初始化的成员mDist.