两圆A完全包含B的充要条件是圆心距≤|r1−r2|且r1≥r2;当r2=0时,B退化为点,只需该点在A内(含边界)即满足包含。

判断两圆包含关系的核心公式
两个圆是否满足“完全包含”,只取决于圆心距离和半径差。设圆 A 圆心为 (x1, y1)、半径 r1,圆 B 为 (x2, y2)、r2,则 A 完全包含 B 的充要条件是:sqrt((x1-x2)*(x1-x2) + (y1-y2)*(y1-y2)) ,且必须保证 <code>r1 >= r2。
注意:这个不等式隐含了两个前提——不能用 r2 - r1,也不能忽略半径大小顺序。如果 r1 ,那 A 不可能包含 B,直接返回 false 更安全。
避免浮点误差导致误判
用 sqrt 计算距离再比较,容易因浮点精度丢精度,尤其在边界附近(比如刚好相切)。更稳妥的做法是两边平方,消去开方:
- 把原式改写为:
(x1-x2)*(x1-x2) + (y1-y2)*(y1-y2) - 但必须先检查
r1 >= r2,否则(r1 - r2)为负,平方后仍为正,会错误通过判断 - 推荐写法:
r1 >= r2 && (dx*dx + dy*dy) ,其中 <code>dx = x1 - x2,dy = y1 - y2
处理退化情况:同心圆或半径为零
标准公式对同心圆(dx == 0 && dy == 0)天然成立,只要 r1 >= r2 就包含;但半径为零时需明确语义:
立即学习“C++免费学习笔记(深入)”;
-
r2 == 0:B 是一个点,只要该点在 A 内(含边界),就满足“完全包含”——此时条件简化为dx*dx + dy*dy -
r1 == 0:A 是一个点,只有当r2 == 0且两圆心重合时才可能“包含”,否则必然 false - 实际工程中建议加注释说明是否把点视为退化圆,避免调用方误解
C++ 实现示例(含内联与 const 正确性)
struct Circle {
double x, y, r;
};
<p>bool contains(const Circle& outer, const Circle& inner) {
if (outer.r < inner.r) return false;
double dx = outer.x - inner.x;
double dy = outer.y - inner.y;
double distSq = dx <em> dx + dy </em> dy;
double radDiff = outer.r - inner.r;
return distSq <= radDiff * radDiff;
}
这里没用 std::hypot 或 sqrt,避免多余开方;参数用 const Circle& 防止误改;函数名直指语义,不叫 isInside 这种易歧义的名称。真正容易漏掉的是:调用前没确认谁是 outer 谁是 inner,传反了结果一定错。


















