この方法:
_bool Point::Intersects(const Line& line) const {
return (line.ContainsPoint(*this, false));
}
_
このエラーの原因:「this」ポインターを「const Line」から「Line&」に変換できませんこの変更:
_bool Point::Intersects(const Line& line) const {
return const_cast<Line&>(line).ContainsPoint(*this, false);
}
_
エラーを修正しますが、問題を修正する正しい方法とは思えません。元のメソッドがエラーと見なされるのはなぜですか?
役立つ場合、ContainsPoint(const Point& point, bool isInfinite)
は非constであり、それが呼び出すすべてのメソッドも非constです。
ある意味で、実際に自分で答えを提供しました。
Intersects
メソッドでは、パラメータline
がconst
として宣言されます。これにより、この変数の使用方法が制限されます。具体的には、const
メソッドのみを呼び出すことができ、const
Lineオブジェクトを期待するメソッドにのみ渡すことができます。
ただし、ContainsPoint
がconst
として宣言されていないことを指摘しました。したがって、上記の要件を満たしていません(つまり、const
オブジェクトでnon _const
メソッドを呼び出すことは許可されていません)。これが元のメソッドがエラーを生成する理由です。また、制限がconst_cast
によって緩和されるため、2番目のバージョンが機能する理由も説明します。
実際の問題は、ContainsPoint
の宣言にあります(また、_const
でもないため、呼び出すメソッドにもおそらくあります)。ここには大きな設計上の欠陥があるようです。 ContainsPoint
の目的は、Point
がLine
にあるかどうかを確認することなので、副作用は予期しないものです。したがって、const
メソッドでない理由はないはずです。実際(そしてあなたの例はこれを示しています)、Line
のユーザーはexpectContainsPoint
がconst
メソッドになります。したがって、実際の解決策は、Line
のようなメソッドがContainsPoint
として宣言され、インスタンスの状態を明確に変更するメソッドのみがconst
クラスの設計を変更することです。非const
以外
この場合、許可されていないconst参照で非constメソッドを呼び出しています。次の2つのオプションがあります。
const_cast
ContainsPoint
をconstメソッドにする問題は実際には単純なものです:
non-constメソッドfoo()を持つクラスAがあり、const Aへの参照を介して非constメソッドfoo()を呼び出しています。
const A& a = ...;
a.foo(); // failed
それがconstの目的です。const変数は、変更されないことを宣言することを意味します。 foo()は「自分自身を変更します」(foo()は非constメソッドであるため、「内部で変更することは合法です」という意味です)、それがコンパイラの不満の理由です。 、しかしその内容を変更するつもりです(foo()を介して)
解決方法は簡単ですが、どの方法が正しいかを知っておく必要があります。
1)foo()がconst refなどを介して呼び出すことが正当であると確信している場合、それをconstメソッドとして宣言する必要があります:A :: foo()const {...}
2)foo()がconstを作成するのに適切でないことを知っている場合は、考慮する必要があります
2.1) "a"を見直して、非constにする方が適切かどうかを確認します。または
2.2)Aで作業を行った別のconstメソッドを見つけます。
(mutableやconst_castを使用するなど、他の方法もありますが、99.9%の時間をかける方法ではありません。したがって、ここでは触れませんでした)