https://biancheng.love/contest-ng/index.html#/123/problems
做题要在纸上弄弄,才会有发现。
发现到答案只是-1和4,因为坐标都是整数。
然后就是找是否存在正方形了。
判断如下:
1、枚举任意两个点,作为正方形的一条边,那么,整个正方形就确定了,有两个方向。
因为,
设坐标为(x1, y1) & (x2, y2),所求的坐标是和x1相连,那么有方程如下。
1、垂直,向量积是0
2、边长相等,然后距离公式化简。
即可解出剩下的两个点。
然后要注意两个点要在正方形的同一侧,不然变了平行四边形了。

#include <cstdio> #include <cstdlib> #include <cstring> #include <cmath> #include <algorithm> #include <assert.h> #define IOS ios::sync_with_stdio(false) using namespace std; #define inf (0x3f3f3f3f) typedef long long int LL; #include <iostream> #include <sstream> #include <vector> #include <set> #include <map> #include <queue> #include <string> struct node { int x, y; bool operator < (const struct node & rhs) const { if (x != rhs.x) { return x < rhs.x; } else return y < rhs.y; } bool operator != (const struct node & rhs) const { return !(x == rhs.x && y == rhs.y); } } arr[2222]; int n; bool check(struct node t1, struct node t2, int one, int two) { int pos = lower_bound(arr + 1, arr + 1 + n, t1) - arr; if (pos == one || pos == two || arr[pos] != t1) return false; pos = lower_bound(arr + 1, arr + 1 + n, t2) - arr; if (pos == one || pos == two || arr[pos] != t2) return false; return true; } void work() { scanf("%d", &n); for (int i = 1; i <= n; ++i) { scanf("%d%d", &arr[i].x, &arr[i].y); } sort(arr + 1, arr + 1 + n); // for (int i = 1; i <= n; ++i) { // cout << arr[i].x << " " << arr[i].y << endl; // } // cout << endl; int ans = 0; for (int i = 1; i <= n; ++i) { for (int j = i + 1; j <= n; ++j) { struct node t[8]; t[0].x = arr[i].y - arr[j].y + arr[i].x; t[0].y = arr[j].x - arr[i].x + arr[i].y; t[1].x = arr[j].y - arr[i].y + arr[j].x; t[1].y = arr[i].x - arr[j].x + arr[j].y; // cout << i << " " << j << endl; // cout << "*********" << endl; // for (int k = 0; k <= 1; ++k) { // cout << t[k].x << " " << t[k].y << endl; // } // cout << "**********" << endl; if (t[0].x < arr[i].x || t[0].x == arr[i].x && t[0].y < arr[i].y) { t[0].x = arr[j].y - arr[i].y + arr[i].x; t[0].y = arr[i].x - arr[j].x + arr[i].y; } if (t[1].x < arr[j].x || t[1].x == arr[j].x && t[1].y < arr[j].y) { t[1].x = arr[i].y - arr[j].y + arr[j].x; t[1].y = arr[j].x - arr[i].x + arr[j].y; } // for (int k = 0; k <= 1; ++k) { // cout << t[k].x << " " << t[k].y << endl; // } if (check(t[0], t[1], i, j)) { printf("4 "); return; } t[0].x = arr[i].y - arr[j].y + arr[i].x; t[0].y = arr[j].x - arr[i].x + arr[i].y; t[1].x = arr[j].y - arr[i].y + arr[j].x; t[1].y = arr[i].x - arr[j].x + arr[j].y; if (t[0].x > arr[i].x || t[0].x == arr[i].x && t[0].y > arr[i].y) { t[0].x = arr[j].y - arr[i].y + arr[i].x; t[0].y = arr[i].x - arr[j].x + arr[i].y; } if (t[1].x > arr[j].x || t[1].x == arr[j].x && t[1].y > arr[j].y) { t[1].x = arr[i].y - arr[j].y + arr[j].x; t[1].y = arr[j].x - arr[i].x + arr[j].y; } // for (int k = 0; k <= 1; ++k) { // cout << t[k].x << " " << t[k].y << endl; // } // cout << endl; if (check(t[0], t[1], i, j)) { printf("4 "); return; } } } assert(ans >= 0); printf("%d ", -1); return; } int main() { #ifdef local freopen("data.txt", "r", stdin); // freopen("data.txt", "w", stdout); #endif int t; scanf("%d", &t); while (t--) work(); return 0; }