题解 P1665 【正方形计数】

· · 题解

简单的三垂直问题

引入

学过全等三角形的都知道三垂直

如图

则易证$AM=BN,MB=CN

把他用到坐标中,与正方形结合

如图一

坐标系上有两点A,BA(2,4),B(4,0);

如图二

坐标系上有另外两点C,D

如图三 坐标系上另有两点C',D' ![03](https://cdn.luogu.com.cn/upload/image_hosting/y7ju4jq1.png?x-oss-process=image/resize,m_lfit,h_170,w_225) $C'(-2,2),D'(0,-2)$使四边形AC'BD'也是正方形 ```cpp struct node { int x,y; }num[3000]; A(num[i].x,num[i].y) B(num[j].x,num[j].y); ``` 若使ABCD为正方形 则 ``` C(num[i].x±(num[i].x-num[j].x),num[i].y±(num[j].y-num[i].y)) D(num[j].x±(num[i].x-num[j].x),num[j].y±(num[j].y-num[i].y)) ``` 所以这道$\color{purple} \text{\textbf{黄题}}$最后只要判断C点,D点是否存在就行了 ------------ # **上DM** ```cpp #include<bits/stdc++.h> using namespace std; inline int read(){ int w=1,q=0;char ch=' '; while(ch!='-'&&(ch<'0'||ch>'9'))ch=getchar(); if(ch=='-')w=-1,ch=getchar(); while(ch>='0'&&ch<='9')q=q*10+ch-'0',ch=getchar(); return w*q; }//快读 struct node { int x,y; }num[3000]; map<pair<int,int>,int >mapp;//因为坐标有负数,所以用map+pair int n,tot=0,ans=0; int main() { //freopen("rect.in","r",stdin); //freopen("rect.out","w",stdout); scanf("%d",&n); for(int i=1;i<=n;i++) { int a,b; a=read(),b=read(); num[i].x=a,num[i].y=b; mapp[make_pair(a,b)]=1; } for(int i=1;i<=n;i++) for(int j=i+1;j<=n;j++) { int u,v; u=num[i].x-num[j].x; v=num[j].y-num[i].y; if(mapp[make_pair(num[i].x+v,num[i].y+u)]==1&&mapp[make_pair(num[j].x+v,num[j].y+u)]==1) ans++; if(mapp[make_pair(num[i].x-v,num[i].y-u)]==1&&mapp[make_pair(num[j].x-v,num[j].y-u)]==1) ans++; } printf("%d",ans/4);//一个正方形重复四遍,所以要除以4 } ``` //重新审核 //增加了Latex,求通过 //<蒟蒻的第一篇题解>