Google Interview Question
Software Engineer / DevelopersCountry: United States
Interview Type: Phone Interview
from math import atan2, degrees
def max_viewing_angle(points, v):
angles = [degrees(atan2(y, x)) for x,y in points]
angles.sort()
start = 0
end = 0
max_points = None
while end < len(angles):
if max_points == None:
max_points = (end-start, angles[start])
diff = angles[end] - angles[start]
if diff <= v:
end += 1
else:
start += 1
points = end - start
if points > max_points[0]:
max_points = (points, angles[start])
return max_points[1] + v/2
points = [(1,1), (3,1), (2,1), (1,2), (-2,5), (-1,6), (1,3), (-1,3), (0,4)]
v = 45.0
print max_viewing_angle(points, v)
Find angles for all the points in 2D. For -ve angles subtract from 360 (only required for ease in code)
System.out.println(Math.atan2(3, 3) * 180 / Math.PI); //45
System.out.println(Math.atan2(3, -3) * 180 / Math.PI); // 135
System.out.println(Math.atan2(-3, -3) * 180 / Math.PI); // -135 // 360 - 135 = 225
System.out.println(Math.atan2(-3, 3) * 180 / Math.PI); // -45 // 360 - 45 = 315
sort angles
int ei = lowerBound(List<Integer> angles, int si, int ei, int ev);
append values from 0 to ei to end of the angles array. // required for search in cicural sorted array. e.g
angles = [1, 20, 45, 134, 260, 359, 361, 380] ..here 380 ==> 1, 390 ==> 20
total points seen in 45 viewing angle from 359 is 3 (359, 361, 380)
int maxpoint(int angles[], ) {
int max = 0;
for(int si = 0; si < angles.length && angles[si] < 361; si ++) {
int ev = angles[si] + 45;
int ei = lowerBound(angles, si, angles.length, ev);
max = Math.max(max, ei - si);
}
return max;
}
int lowerbound(List<Inetger> angles, int si, int ei, int ev) {
if(si >= ei) return si;
while(si < ei) {
int mi = (si + ei)/2
int mv = angles[mi];
if(mv = ev) return mi;
if(mv > ev) {
ei = mi;
} else {
si = mi;
}
}
return si;
}
#include <iostream>
#include <vector>
#include <map>
#include <cmath>
#define PI 3.14159265
using namespace std;
struct Point{
double x, y;
};
int get_angle(const Point& p){
return atan2 (p.y,p.x) * 180 / PI;
}
int best_angle(const vector<Point>& points, int v_angle){
int res = 0;
multimap<int, Point> mm;
for(int i = 0 ; i < points.size(); ++i){
mm.insert(pair<const int, Point>(get_angle(points[i]), points[i]));
cout << get_angle(points[i]) << " " << points[i].x << " " << points[i].y << endl;
}
int current_angle = 0;
auto iter = mm.begin(), iterE = mm.begin();
while(iterE != mm.end() && current_angle <= v_angle){
++iterE;
if(res < current_angle)
res=current_angle;
current_angle = iterE->first - iter->first;
}
while(iterE != mm.end()){
if(current_angle == v_angle){
res = current_angle;
break;
}
else if(current_angle > v_angle){
++iter;
} else{
++iterE;
if(res < current_angle)
res = current_angle;
}
current_angle = iterE->first - iter->first;
}
return res;
}
void test(int case_n, const vector<Point>& vp, int v){
cout << "test case " << case_n << " :" << endl;
cout << "input : " << endl;
cout << "angle : " << v << endl;
cout << "points : " << endl;
int a = best_angle(vp, v);
cout << "output : " << a << endl;
cout << "-----------------------" << endl << endl;
}
int main() {
test(1, vector<Point>({{10,10}, {10,5}, {6,8}, {1,9}, {9,4}}), 0);
test(2, vector<Point>({{10,10}, {10,5}, {6,8}, {1,9}, {9,4}}), 15);
test(3, vector<Point>({{10,10}, {10,5}, {6,8}, {1,9}, {9,4}}), 45);
test(4, vector<Point>({{10,10}, {10,5}, {6,8}, {3,9}, {9,4}}), 0);
test(5, vector<Point>({{10,10}, {10,5}, {6,8}, {3,9}, {9,4}}), 45);
test(6, vector<Point>({{10,10}, {10,5}, {6,8}, {3,9}, {9,4}}), 60);
test(7, vector<Point>({{10,10}, {10,5}, {6,8}, {4,9}, {9,4}}), 31);
test(8, vector<Point>({{10,10}, {10,5}, {6,8}, {4,9}, {9,4}}), 72);
test(9, vector<Point>({{10,10}, {10,5}, {6,8}, {4,9}, {9,4}}), 180);
return 0;
}
1. find angle of all points from x axis
- shivamkmrjha November 18, 20162. sort on basis of angle
3. use sliding window to find mamimum number of elemnts that can be present in window and having angle less than 45 deg from 1st element of window