解题思路
用类似字符串哈希的思想,一个int表示一个点,点的定义为 x*13131 + y,保证每个点有唯一的值;
建立两个哈希表,点和其数量的映射,同一x值和对应所有y值的映射;
对于每次添加,往表里加点;
对于每次查询,遍历同一x的y值们,跳过相同点,由查询点(x,y)和遍历到的点(x,next_y)可以确定左右两边两种正方形;
如果对应的点存在,组成的正方形个数就是对应两点个数乘积。
代码
class DetectSquares {
public:
unordered_map<int, int> points; //点和其数量
unordered_map<int, vector<int> > x_point; //同一x值对应的y值们
int seed = 13131;
DetectSquares() {
}
void add(vector<int> point) {
int p = point[0] * seed + point[1];
points[p]++;
x_point[point[0]].push_back(point[1]);
}
int count(vector<int> point) {
int x = point[0], y = point[1];
int cnt = 0;
for(auto next_y : x_point[x]) {
int dis = next_y - y; //可以不用abs,下面包含两边的情况
if(dis == 0) continue; //同一点,跳过
int left1 = (x - dis) * seed + y, left2 = (x - dis) * seed + next_y;
int right1 = (x + dis) * seed + y, right2 = (x + dis) * seed + next_y;
if(points.count(left1) && points.count(left2)) cnt += points[left1] * points[left2];
if(points.count(right1) && points.count(right2)) cnt += points[right1] * points[right2];
}
return cnt;
}
};
/**
* Your DetectSquares object will be instantiated and called as such:
* DetectSquares* obj = new DetectSquares();
* obj->add(point);
* int param_2 = obj->count(point);
*/