package evaluation;

public class Evaluate {
	
	private int x1, y1, x2, y2;
	
	public Evaluate (int x1, int y1, int x2, int y2)
	{
		this.x1 = x1;
		this.y1 = y1;
		this.x2 = x2;
		this.y2 = y2;
	}
	
	public static int area (int x1, int y1, int x2, int y2) {
        return (x2 - x1) * (y2 - y1);
    }
	
    public double overlapArea (int x1, int y1, int x2, int y2) {
    	
        int xMin = Math.max(this.x1, x1);
        
        int xMax = Math.min(this.x2, x2);

        int yMin = Math.max(this.y1, y1);
        
        int yMax = Math.min(this.y2, y2);

        // find area of this
        // zero if they do not overlap

        if ((yMin > yMax) || (xMin > xMax))
            return 0.0;

        double overlap = area(xMin, yMin, xMax, yMax);

        return overlap;

    }
    
    public double matchQuality(int x1, int y1, int x2, int y2) {
        return 2 * overlapArea(x1,y1,x2,y2) / (area(this.x1,this.y1,this.x2,this.y2) + area(x1,y1,x2,y2));
    }

    public double WolfSigma (int x1, int y1, int x2, int y2) {
        return overlapArea(x1,y1,x2,y2) / (area(this.x1,this.y1,this.x2,this.y2));
    }
    
    public double WolfPi (int x1, int y1, int x2, int y2) {
        return overlapArea(x1,y1,x2,y2) / (area(x1,y1,x2,y2));
    }
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
	
	/*static private int truepos;
	static private int trueneg;
	static private int falsepos;
	static private int falseneg;
	
	public int getTruePositives () {
		return truepos;
	}
	
	public int getTrueNegatives () {
		return trueneg;
	}
	public int getFalsePositives () {
		return falsepos;
	}
	
	public int getFalseNegatives () {
		return falseneg;
	}
		
	public static double Precision (int tp, int fp)
	{
	    if(tp + fp == 0) return 0;

	    return (double)tp/(double)(tp + fp);
	}

	public static double Recall(int tp, int fn)
	{
	    if(tp + fn == 0) return 0;

	    return (double)tp/(double)(tp + fn);
	}
	
	public static int MaximumValue(int[] label, int n) {
		int max = Integer.MIN_VALUE;
		for (int i = 0; i < n; i++) {
			if (label[i] > max) {
				max = label[i];
			}
		}
		return max;
	}
			
	public static double FMeasure(double precision, double recall)
	{
	    if(precision + recall == 0) return 0;

	    return 2*(precision*recall)/(precision + recall);
	}
		
	public static double ComputeBinFMeasure(BufferedImage label, BufferedImage mask)
	{
	    if(label == null || mask == null) return -1;

	    BinConfMatrix (label, mask);

	    double f = FMeasure(Precision(truepos,falsepos), Recall(truepos, falseneg));

	    return f;
	}
	
	public static int getRegionArea (int label, BufferedImage img)
	{
	    int width  = img.getWidth(null);
	    int height = img.getHeight(null);
				    
	    int n = width*height;
	    
	    int area = 0;

	    int[] array = Util.transformBufferColorImage(img);
	    
	    for(int p = 0; p < n; p++)
	    {
	        if(array[p] == label)
	        {
	            area++;
	        }
	    }
	    return area;
	} 
	
	public static int getIntersectionArea (int label1, BufferedImage img1, int label2, BufferedImage img2)
	{
		if(img1 == null || img2 == null) return -1;
		
		if( (img1.getWidth(null) !=  img2.getWidth(null)) || (img2.getHeight(null) !=  img2.getHeight(null)) ) return -1;

	    int width  = img1.getWidth(null);
	    int height = img1.getHeight(null);
			    
	    int n = width*height;
	    
	    int intersection = 0;

	    int[] array1 = Util.transformBufferColorImage(img1);
	    int[] array2 = Util.transformBufferColorImage(img2);
	    
	    for(int p = 0; p < n; p++)
	    {
	        if((array1[p] == label1) && (array2[p] == label2))
	        {
	            intersection++;
	        }
	    }
	    return intersection;
	}
	
	public static double ma (int label1, BufferedImage img1, int label2, BufferedImage img2) 
	{
		int img1_area = getRegionArea (label1, img1);
		int img2_area = getRegionArea (label2, img2);
		int intersection = getIntersectionArea (label1, img1, label2, img2);
		return ( (double)(2 * intersection) / (double)(img1_area + img2_area) );
	}
	
	public static double m (int label, BufferedImage img1, int N, BufferedImage img2) 
	{
		double max = -Double.MAX_VALUE;
		
		for (int i = 0; i < N; i++) {
			double m = ma (label, img1, i, img2);
			if (m > max) {
				max = m;
			}
		}
		return max;
	}
	
	public static double icidar_precision (BufferedImage labels, BufferedImage groundtruth) {
		
		int E = getNumberOfImageComponents (labels);
		int T = getNumberOfImageComponents (groundtruth);
		
		double sum = 0;
		
		for (int i = 0; i < E; i++) {
			sum += m (i, labels, T, groundtruth);  	
		}
		
		return sum / ( (double) E );
	}

	public static double icidar_recall (BufferedImage labels, BufferedImage groundtruth) {
		
		int E = getNumberOfImageComponents (labels);
		int T = getNumberOfImageComponents (groundtruth);
		
		labels.ge
		
				
		double sum = 0;
		
		for (int i = 0; i < T; i++) {
			sum += m (i, groundtruth, E, labels);  	
		}
		
		return sum / ( (double) T );
	}
	
	
	
	public static boolean BinConfMatrix (BufferedImage label, BufferedImage mask)
	{
	    if(label == null || mask == null) return false;

	    int lwidth  = label.getWidth(null);
	    int lheight = label.getHeight(null);
	    
	    int mwidth  = mask.getWidth(null);
	    int mheight = mask.getHeight(null);
			    
	    if(lwidth != mwidth || lheight != mheight) return false;

	    int n = lwidth*lheight;
	    
	    int tp = 0, tn = 0, fp = 0, fn = 0;

	    int[] larray = Util.transformBufferColorImage(label);
	    
	    int[] marray = Util.transformBufferColorImage(mask);
	    
	    int lbmax = MaximumValue(larray, n), maskmax = MaximumValue(marray, n);

	    for(int p = 0; p < n; p++)
	    {
	        if(larray[p] == lbmax)
	        {
	            if(marray[p] == maskmax)
	                tp++;
	            else
	                fp++;
	        }else{

	            if(marray[p] == maskmax)
	                fn++;
	            else
	                tn++;
	        }
	    }

	    truepos  = tp;
	    trueneg  = tn;
	    falsepos = fp;
	    falseneg = fn;
	    
	    System.out.println("tp : " + tp + " tn : " + tn + " fp : " + fp + " fn : " + fn);

	    return true;
	} */
}
