線段的計算。也是計算幾何的基礎之一。判斷兩線段相交,求交點,等都是必不可少的內容。
常用的解析幾何方法使用三角函式和除法,使得計算的代價較高&&容易產生較大的誤差。如計算兩條近似平行的直線y=kx+b,的交點,涉及到了除法運算。那麼對計算機的精確度要求就非常高了。因此 如果能夠在計算的時候,只涉及到+,-,*,〉,〈,等簡單的運算,那麼產生的誤差就會非常小,而且演算法簡捷,高效。
如何判斷兩直線相交。分兩步判斷,分別是:1.快速排斥實驗。2.跨立實驗。注意,這裡是兩步,不是兩種方法。第一步不符合直接就不符合了。無需進行第二步實驗。
1.快速排斥實驗:判斷兩直線為所在的矩形的對角線的兩個矩形是否相交。
2.跨立實驗:如果兩線段相交,則兩線段必然相互跨立對方。
如圖所示的點。如果相交,則必定存在向量(b1,a1)和向量(b1,a2)在向量(b1,b2)的兩側。
即:((b1,a1)叉乘(b1,b2))*((b1,a2)叉乘(b1,b2))<0
所以有兩線段相交,存在:((b1,a1)叉乘(b1,b2))*((b1,a2)叉乘(b1,b2))<=0
那麼,因為向量的叉積是向量,因此存在兩種判定方法,即:(a1,a2)跨立(b1,b2)和(b1,b2)跨立(a1,a2)。
具體情況分類討論即可。
code:
int lineinter(v l1,v l2)
}return 0;
}
後來習慣直接過載^後用點來當向量進行叉乘,寫乙個^叉乘**:
struct point
friend point operator - (const point &a,const point &b)
friend double operator ^ (const point &a,const point &b)
};struct v
};int lineinter(v l1,v l2)return 0;
}
oj測試:51nod-1264-線段相交(板子)複製貼上,直接a。
poj-1127-jack straws(線段相交+聯通)
題目大意:給出一些線段,相交的線段之間能夠聯通。然後每輸入兩個線段,判斷這兩個線段之間有沒有關係。
思路:判斷線段相交,然後floyd聯通。
accode:
// luogu-judger-enable-o2
//#pragma comment(linker, "/stack:1024000000,1024000000")
#include#include#include//#include#include#include#include#include#include#include#include#include#includeusing namespace std;
#define ll long long
#define pair pair//#define max(a,b) (a)>(b)?(a):(b)
//#define min(a,b) (a)
#define clean(a,b) memset(a,b,sizeof(a))// 水印
//std::ios::sync_with_stdio(false);
// register
const int maxn=1e2+10;
const int inf32=0x3f3f3f3f;
const ll inf64=0x3f3f3f3f3f3f3f3f;
const int mod=998244353;
const double pi=acos(-1.0);
const double eps=1.0e-12;
struct point
friend point operator + (const point &a,const point &b)
friend point operator - (const point &a,const point &b)
friend point operator == (const point &a,const point &b)
}return 0;
}int mp[maxn][maxn];
void intt()
int main()
for(int i=1;i<=n;++i)
}} for(int k=1;k<=n;++k)
}} int a,b;
while(~scanf("%d%d",&a,&b))
}}
若已知兩線段相交,可以用解析幾何的方法計算求得交點,這時其運算時可靠的,誤差也可以降低到可接受的程度。不過,這樣沒有利用我們在判斷相交時計算出的叉積,造成了運算上的重複和浪費。
首先補全 多邊形abcd,向量叉積可以當作面積。
}補充:上面的**明顯較為複雜,容易出錯。觀察發現,好多變數是重複出現的,因此我們可以用乙個變數來代替他們:
new code:
point lineinterdot(v l1,v l2)
叉乘的板子:
point lineinterdot(const v &l1,const v &l2)
利用叉積進行求取直線交點(前提:已經確定兩直線相交,(兩直線不平行))
code:
point lineinterdot(const v &l1,const v &l2)
使用叉乘進行直接判斷。
code:
int parellel(const v &x,const v &y)
if(sl.intersect(s,s->below,singlepoint))
} else if(e->type==right)
}} else
}if(sl.intersect(se1,se1->below,singlepoint))
}}eq->remove(e);//元素處理完畢,將其彈出
}return 1;
}
計算幾何 線段
首先是直線相交,這個簡單,就是看斜率,斜率不同則相交。重點分析線段與線段相交,給你兩組座標p1 x1,y1 p2 x2,y2 q1 x3,y3 q2 x4,y4 判斷p1p2與q1q2是否相交 首先可以很快排除下面四種情況 對於第 種情況滿足條件 max q1.x,q2.x max q1.x,q2....
計算幾何 線段相交
問題描述 已知兩條線段p1p2和q1q2,判斷p1p2和q1q2是否相交,若相交,求出交點。兩條線段的位置關係可以分為三類 有重合部分 無重合部分但有交點 無交點。演算法的步驟如下 1.快速排斥實驗。設以線段p1p2為對角線的矩形為r,設以線段q1q2為對角線的矩形為t,如果r和t不相交,則兩線段不...
計算幾何 幾何基礎
這章早在2017年寒假就在培訓的時候由來自清華的hta老師上過了 但是本蒟蒻那時候並不是懂的太多 所以這週ww老師又上了一遍 大概記錄一下 大概就跟高中必修4的平面向量差不多 有上過的應該都會 a x1,y1 b x2,y2 a b x1x2 y1y2 a b a b cos a,b 運用 若a與b...