Max Points on a Line

题目描述:

Given n points on a 2D plane, find the maximum number of points that lie on the same straight line.

给n个点,看最多多少个点在同一条线。

我真的服了自己,一开始想那么麻烦,还去求y=kx+b。最后还有问题,因为当k失去精度后,b的计算可能不相等。

下面是一段非常复杂的计算,还没有成功,就当复习了hashcode和equals用法!

这里将所有的直线全部计算出来,包括水平线,竖直线,以及各种不同的k,b组成的线。太麻烦了!!!

这个题还有一点就是所给的点可能有重复的,这个地方要处理好。

class Point {
	int x;
	int y;
	Point() { x = 0; y = 0; }
	Point(int a, int b) {
		x = a; y = b; 
	}
}

class Line{
    double k;
    double b;
    Line(){
        k = 0; b = 0; 
    }
    Line(double k, double b) {
        this.k = k; this.b = b; 
    }
    @Override
    public int hashCode() {
        final int prime = 31;
        int result = 1;
        long temp;
        temp = Double.doubleToLongBits(b);
        result = prime * result + (int) (temp ^ (temp >>> 32));
        temp = Double.doubleToLongBits(k);
        result = prime * result + (int) (temp ^ (temp >>> 32));
        return result;
    }
    
    @Override
    public boolean equals(Object obj) {
        if (this == obj)
            return true;
        if (obj == null)
            return false;
        if (getClass() != obj.getClass())
            return false;
        Line other = (Line) obj;
        if (Double.doubleToLongBits(b) != Double.doubleToLongBits(other.b))
            return false;
        if (Double.doubleToLongBits(k) != Double.doubleToLongBits(other.k))
            return false;
        return true;
    }
}

public class Solution149 {
    public int maxPoints(Point[] points) {
        if(points.length==1||points.length==2)
            return points.length;
        int kind=1,sum=1;
        for(int i=1;i<points.length;i++){
            if(points[i].x==points[0].x&&points[i].y==points[0].y)
                sum++;
            else{
                kind++;
                break;
            }
        }
        if(kind==1)
            return sum;
        int maxpoint=0,n=points.length;
        Map<Integer, Integer> horizenMap=new HashMap<Integer, Integer>();
        Map<Integer, Integer> verticalMap=new HashMap<Integer, Integer>();
        Map<Line, Integer> lineMap=new HashMap<Line, Integer>();
        for(int i=0;i<n;i++){
            boolean horizenflag=true;
            boolean verticalflag=true;
            Set<Double> kSet=new HashSet<Double>();
            for(int j=0;j<n;j++){
                if(i==j||(points[i].y==points[j].y&&points[i].x==points[j].x))
                    continue;
                if(points[i].x==points[j].x&&points[i].y!=points[j].y){
                    if(verticalflag){
                        if(!verticalMap.containsKey(points[i].x))
                            verticalMap.put(points[i].x,1);
                        else
                            verticalMap.put(points[i].x,verticalMap.get(points[i].x)+1);
                        verticalflag=false;
                    }
                }
                else if(points[i].y==points[j].y&&points[i].x!=points[j].x){
                    if(horizenflag){
                        if(!horizenMap.containsKey(points[i].y))
                            horizenMap.put(points[i].y,1);
                        else
                            horizenMap.put(points[i].y,horizenMap.get(points[i].y)+1);
                        horizenflag=false;
                    }
                }else{
                    double k=1.0 * (points[i].y - points[j].y) / (points[i].x - points[j].x);
                    double b=points[j].y-k*points[j].x;
                    if(!kSet.contains(k)){
                        Line line=new Line(k, b);
                        if(!lineMap.containsKey(line))
                            lineMap.put(line, 1);
                        else
                            lineMap.put(line, lineMap.get(line)+1);
                        kSet.add(k);
                    }
                }
            }
        }
        for(Integer key:horizenMap.keySet())
            maxpoint=horizenMap.get(key)>maxpoint?horizenMap.get(key):maxpoint;     
        for(Integer key:verticalMap.keySet())
            maxpoint=verticalMap.get(key)>maxpoint?verticalMap.get(key):maxpoint; 
        for(Line key:lineMap.keySet())
            maxpoint=lineMap.get(key)>maxpoint?lineMap.get(key):maxpoint;
    return maxpoint;
    }
}
后来想起来每次经过一个点,就将这个点能够经过的所有直线所包含最多的点算出来就行了!!

写了下面一段代码,AC了,思路清晰就能节约很长时间,所以一定要想清楚再动手才能提高效率!


public class Solution {
    public int maxPoints(Point[] points) {
        if(points.length<3)
            return points.length;
        int maxpoint=0,n=points.length;
        int result=0;
        Map<Double, Integer> lineMap=new HashMap<Double, Integer>();
        for(int i=0;i<n;i++){
            maxpoint=0;lineMap.clear();
            int horizenNum=0,verticalNum=0;
            int dumplicate=0;
            for(int j=0;j<n;j++){
                if(i==j||(points[i].y==points[j].y&&points[i].x==points[j].x))
                    dumplicate++;
                else if(points[i].x==points[j].x&&points[i].y!=points[j].y)
                    verticalNum++;
                else if(points[i].y==points[j].y&&points[i].x!=points[j].x)
                    horizenNum++;
                else{
                    double k=1.0 * (points[i].y - points[j].y) / (points[i].x - points[j].x);
                    if(!lineMap.containsKey(k))
                        lineMap.put(k,1);
                    else
                        lineMap.put(k,lineMap.get(k)+1);
                }
            }
            horizenNum+=dumplicate;
            verticalNum+=dumplicate;
            maxpoint=horizenNum>verticalNum?horizenNum:verticalNum;
             for(Double key:lineMap.keySet())
                 maxpoint=lineMap.get(key)+dumplicate>maxpoint?lineMap.get(key)+dumplicate:maxpoint;
            result=maxpoint>result?maxpoint:result;
        }
        return result;
    }
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值