我是新来的。我正在解决一个问题,检查N点(x,y)是否形成正方形。最终输出是点可以形成的平方数+最大区域(正方形之一)。 输入如下:
6
1 1
1 2
1 3
2 3
2 2
2 1
输出:
2 -> (2 Squares were formed)
1 -> (1 was the biggest area)
所以我正在读这样的x和y:
cin >> n;
for(int i=0;i<n;i++)
{cin >> coordenadas[i].x >> coordenadas[i].y;concat[i]=coordenadas[i].y * 100000 + coordenadas[i].x;}
sort (concat, concat+n);
for(int i=0;i<n;i++)
{
A.x=coordenadas[i].x;A.y=coordenadas[i].y;
for(int ii=M;ii<n;ii++)
{
B.x=coordenadas[ii].x;
B.y=coordenadas[ii].y;
...
calculo();
if(mArea<area)
mArea=area;
}
M+=1;
}
在下一个函数中,我试图计算x和y var来得到像这样的值 - &gt; http://i.stack.imgur.com/Uqtau.png
但我对我的计算不确定。
我的计算功能:
void calculo()
{
int x=0,y=0;
if(A.x==B.x)
{
x=abs(B.y-A.y);
area=x*x;
R1.c1=(B.y) * 100000 + (A.x + x);
R1.c2=(B.y) * 100000 + (A.x - x);
if (binary_search (concat, concat+n, R1.c1))
if (binary_search (concat, concat+n, R1.c2))
quadrados+=1;
else
area=0;
}
else
{
x=abs(B.y-A.y);
y=abs(B.x-A.x);
area=sqrt(x*x+y*y)*sqrt(x*x+y*y);
R1.c1=(B.y + y) * 100000 + (B.x - x);
R1.c2=(A.y + y) * 100000 + (A.x - x);
if (binary_search (concat, concat+n, R1.c1))
if (binary_search (concat, concat+n, R1.c2))
quadrados+=1;
else
area=0;
}
}
我正在做的是,挑选2个独特的点并计算形成正方形的其他两个点。然后我&#34; concat&#34;它们变成一个唯一的整数(例如。(By + y)* 100000 +(Bx - x),这意味着 - > y * 100000 + x)然后我用二分搜索寻找它们,如果找到它我会增加n_square变种。
问题是,我不确定计算是否正常,我需要一手这个。我知道有一种方法可以用bitset计算,但我不是专家,所以我不能使用bitset。我试图获得O(N ^ 2 * log(V))解决方案。给我一些提示
###################在一些评论后的新编辑 - &gt; ###################
新输入(评论)
9
5 3
1 4
1 3
1 2
2 1
2 3
3 4
3 2
4 2
输出:
6 (Number of Squares)
0 (Its Area-> I'm not calculating yet)
预期产出
3
5 (Area)
新守则:
#include <iostream>
#include <algorithm>
#include <vector>
#include <cmath>
using namespace std;
struct c{
int x,y;
}A,B,C,D,coordenadas[3001];
int quadrados=0,n=0;
long int area;
long int concat[3001];
int dist2 (c A,c B) {
int x = A.x - B.x;
int y = A.y - B.y;
return x*x + y*y;
}
void calculo()
{
int d = dist2(A, B);
const int x = B.x - A.x;
const int y = B.y - A.y;
C.x = A.x - y;
C.y = A.y + x;
D.x = B.x - y;
D.y = B.y + x;
d = dist2(A, B);
if (dist2(A, C) == d && 2*d == dist2(B, C))
if (binary_search (concat, concat+n, C.y * 100000 + C.x))
if (dist2(B, D) == d && dist2(C, D) == d)
if (binary_search (concat, concat+n, D.y * 100000 + D.x))
{
quadrados+=1;
}
}
int main() {
int M=1,mArea=0;
cin >> n;
for(int i=0;i<n;i++)
{cin >> coordenadas[i].x >> coordenadas[i].y;concat[i]=coordenadas[i].y * 100000 + coordenadas[i].x;}
sort (concat, concat+n);
for(int i=0;i<n;i++)
{
A.x=coordenadas[i].x;
A.y=coordenadas[i].y;
for(int ii=M;ii<n;ii++)
{
B.x=coordenadas[ii].x;
B.y=coordenadas[ii].y;
calculo();
if(mArea<area)
mArea=area;
}
M+=1;
}
if(quadrados==0)
cout << quadrados << endl;
else
cout << quadrados << endl << mArea << endl;
return 0;
}
答案 0 :(得分:2)
从你的照片中:
const int x = B.x - A.x;
const int y = B.y - A.y;
C.x = A.x - y;
C.y = A.y + x;
D.x = B.x - y;
D.y = B.y + x;
然后
area = x * x + y * y;
答案 1 :(得分:-1)
我假设所有坐标都是整数,并且您选择的类型可以适合最大坐标的平方的两倍(在您的情况下为8亿 - 不是很难)。如果需要,可以省略后一种假设,但前者并不容易,因为否则你必须决定如何处理舍入。
基本思路是循环遍历每个点A和每个点B出现在列表后面而不是A.计算
int dist2 (A, B) {
int x = A.x - B.x;
int y = A.y - B.y;
return x*x + y*y;
}
int d = dist2(A, B);
这样d
是A和B之间的平方距离。现在定义
c C1, C2, D;
C1.x = 2*A.x - B.y;
C1.y = B.x;
C2.x = B.y;
C2.y = 2*A.y - B.x;
并检查C1(resp。,C2)是否在B之后的列表中。如果是,请将其称为C并检查是否
dist2(B, D) == d && dist2(C, D) == d
如果是这样,ABCD就是一个正方形。如果总共有n个元素,则前两个循环发生n(n-1)/ 2次,每对导致2或3次查找,表明算法在时间O(n ^ 2 log n)内运行。
编辑:早期版本还提供了一个更简单的算法,该算法在时间O(n ^ 3)内运行。它的存在引起了混乱,所以我删除它并使其他算法更明确。