Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/python-3.x/18.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ c++;封装问题_C++ - Fatal编程技术网

C++ c++;封装问题

C++ c++;封装问题,c++,C++,我正在尝试使用std::sort和自定义比较函数。为此,我有一个名为trySort的类。这是trySort类的示例代码: trySort.h class trySort { public: private: std::string sortThis; }; class trySort { public: std::string sortThis; private: }; trySort.cpp bool sortThisAsc (const

我正在尝试使用std::sort和自定义比较函数。为此,我有一个名为
trySort
的类。这是
trySort
类的示例代码:

trySort.h

class trySort {

public:

private:
    std::string sortThis;
};
class trySort {

public:
      std::string sortThis;

private:           
};
trySort.cpp

bool sortThisAsc (const trySort & rhs , const trySort & lhs) {
    return lhs.sortThis > rhs.sortThis;
}
bool sortThisAsc (const trySort & rhs , const trySort & lhs) {
    return lhs.sortThis > rhs.sortThis;
}
如果成员
排序此
为私有,则会引发错误

如果我让这个成为像这样的公众成员

trySort.h

class trySort {

public:

private:
    std::string sortThis;
};
class trySort {

public:
      std::string sortThis;

private:           
};
trySort.cpp

bool sortThisAsc (const trySort & rhs , const trySort & lhs) {
    return lhs.sortThis > rhs.sortThis;
}
bool sortThisAsc (const trySort & rhs , const trySort & lhs) {
    return lhs.sortThis > rhs.sortThis;
}
…它会起作用的。看起来好像我让
sort这
成为了一名公众成员

所以我的问题是:如果我这样做,我不是在封装我的数据吗

如果是这样,除了将其作为公共成员之外,还有哪些其他可能的方法?

使用friend:

class trySort {
friend bool sortThisAsc (const trySort & rhs , const trySort & lhs);

private:
       std::string sortThis;
}

它将只允许访问此函数,而不允许访问其他任何内容

编辑这将消除您提到的编译错误,但只能将非成员函数传递给std::sort(),因此这不太有效

在cpp文件中,将函数定义更改为

bool sortThisAsc (const trySort & rhs , const trySort & lhs) {

如果没有
trySort::
函数未在
trySort
类作用域中定义(即,在该类之外),因此如果您尝试在
trySort
中访问私有变量,编译器会发出投诉


这样,您可以按照最初的要求将其作为私有方法保留。

您可以将
操作符>
添加到
trySort
类中

trySort.h

class trySort {

public:
    bool operator >(trySort const &other) {
        return sortThis > other.sortThis;
    }  
private:
    std::string sortThis;
}
如果您需要更大的灵活性(一些其他类型的比较),只需使用getter函数封装
或此

trySort.h

class trySort {

public:
    std::string const &getSortThis() const {
        return sortThis;
    }

private:
    std::string sortThis;
}
如果您完全确定
排序此
在项目过程中始终是不可变的,因此在构造函数中初始化,则可以将其保留为public const成员,但在大多数情况下,这是一种非常推测性的方法

trySort.h

class trySort {

public:
    trySort(std::string const sortThis)
        : sortThis(sortThis) {
    }

    const std::string sortThis;
}

或者你可以用
朋友
,但我会把它作为最后的手段,因为在大多数情况下,它表现出过度的亲密(你总是可以采取一些其他方法来避免使用
朋友
)。在某些情况下,使用
friend
可能是合适的,但它绝不会破坏封装,不同的是
friend
子句向类的客户端发出破坏是故意的信号。

至少有两种选择。 您可以向该数据成员声明公共getter,例如

class trySort {

public:
       const std::string & get_string() const { return sortThis; }

private:
       std::string sortThis;
}
然后在函数sortThisAsc中写入

bool sortThisAsc (const trySort & rhs , const trySort & lhs) {
    return lhs.get_string() > rhs.get_string();
}
或者可以将该函数声明为类的友元函数

class trySort {

public:
       friend bool sortThisAsc (const trySort & rhs , const trySort & lhs);

private:
       std::string sortThis;
}

在这种情况下,函数定义将不会更改。

我建议不要按类中不可公开读取的内容进行排序。我很难想出一些例子来说明什么时候隐藏信息是有意义的,但允许用户按信息排序。为什么不让sortThisAsc成为这个类的一员?@AliAlamiri ok thanksBTW:LHS和RHS的意思是“左手边”和“右手边”,所以如果切换参数,就更清楚了(并相应地改变表达)。@AliAlamiri这就是我的答案。我猜你的朋友bool sortThisAsc(const trySort&rhs,const trySort&lhs);应该是公共的?不是私有的?@user3175729不,不是真的。访问说明符不适用于朋友。它们可以在任何地方指定。除非在标题中声明了sortThisAsc,否则这将不起作用。如果我这样做,我想我在尝试进行排序时可能会出错(vector.begin();vector.end()sortThisAsc)我可能错了,但只有当函数在类中声明为静态时才可能。不,实际上我们都错了。只有自由的非成员函数才能工作。好的,我想我会使用运算符重载方法。thanksit是
运算符True,值得注意。但是另一个
std::sort
签名与
comp
fun一起工作action,在本例中是
sortThisAsc
。主要问题是关于封装。