[英]C++ std::sort with predicate function in Class
我想在某個類中按某種順序對某個結構的向量進行排序。 我在類中編寫了struct和predicate函數的定義,並在具有這些struct和function的類的方法中運行std :: sort。 但是發生了編譯錯誤。 gcc版本是4.0.1,OS是Mac OSX。 代碼如下:
class sample {
public:
struct s {
int x;
int y;
};
bool cmp (struct s a, struct s b) {
if (a.x == b.x)
return a.y < b.y;
else
return a.x < b.x;
}
int func(void) {
std::vector <struct s> vec;
// ...
sort(vec.begin(), vec.end(), cmp); // compilation error
// ...
return 0;
}
};
int main(void) {
sample *smp = new sample();
smp->func();
return 0;
}
錯誤消息龐大而復雜。 所以這是前兩行。
sortSample.cpp:在成員函數'int sample :: func()'中:
sortSample.cpp:51:error:類型'bool(sample ::)(sample :: s,sample :: s)'的參數與'bool(sample :: *)不匹配(sample :: s,sample :: S)”
...
代替上述方法,代碼可以通過以下方式正確運行。
class sample
之外定義struct s
和function cmp()
。 cmp()
並定義<
in struct s
運算符重載。 每種方法的示例代碼如下。
1)
struct s {
int x;
int y;
};
bool cmp (struct s a, struct s b) {
if (a.x == b.x)
return a.y < b.y;
else
return a.x < b.x;
}
class sample {
// ...
2)
struct s {
int x;
int y;
bool operator<(const struct s & a) const {
if (x == a.x)
return y < a.y;
else
return x < a.x;
}
};
任何人都可以告訴這種行為的機制嗎? 為什么第一種方法會調用編譯錯誤?
謝謝。
在第一種情況下, cmp
被聲明為class sample
的成員函數,因此需要this
指針來調用它。 由於this
指針不可用,編譯器正在抱怨它。 您可以通過將cmp
聲明為static
函數來使其工作,因為靜態函數不需要此指針進行調用。 在第二種情況下,由於cmp再次被聲明為獨立函數,因此它的行為與靜態函數相同。 在第三種情況下(使用重載運算符),排序算法將負責為向量中的每個對象調用函數,從而進行編譯。
由於cmp
與任何特定的樣本實例無關,因此將其設為靜態成員函數。
可以在您的可能性中列出的第三種方法是使用operator():
bool operator() (const s& a, const s& b) const
{
if (a.x == b.x)
return a.y < b.y;
else
return a.x < b.x;
}
sort(vec.begin(), vec.end(), *this);
我認為在類之外定義cmp
是最好的,因為當你需要它來訪問類中的一些私有特性時,你應該只將一個函數作為一個成員函數,從邏輯上講,它在那里是合適的。 cmp
只是一個實用程序函數,它為您的類sample
提供了實現的功能,但實際上並不需要訪問私有成員。 此外,它可能不會在對象的上下文中調用(它的唯一操作在其參數上工作;在this
指針上沒有任何內容),也不能在類sample::cmp
的上下文中調用它。 雖然看起來似乎是一個微不足道的觀點,但通常給予函數或代碼不必要的訪問寬度可能是許多軟件錯誤或設計卷積的來源的開始。
執行上述操作的額外好處是,您對std::sort
調用將起作用,這可以回答您的問題。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.