Closest points project

Suggested reading: sections 9.2-9.5

The closest points example revisited

In chapter nine we are going to be studying objects. In their most basic form objects are made up of member variables, or bundles of closely related data items.

Here is one of the examples from the last lecture rewritten to use a simple object. The closest points example is a natural candidate for this approach, since a point is a pair of coordinates.

Here is the declaration for a simple Point class that we can use to represent points. Each point contains two data members, variables x and y that store the coordinates of the point.

public class Point {
    public double x;
    public double y;

    public Point(double x,double y) {
        this.x = x;
        this.y = y;
    }
}

The Point class also contains a special method, called a constructor, that is designed to initialize the x and y member variables from a pair of values provided by the caller.

Here now is the closest points example rewritten to make use of Point objects. By restructuring the data in the program as a list of Point objects we no longer need to use a two dimensional array to store the point data.

public class ClosestPoints {

    /**
     * Read 1000 points from points.txt.
     */
    public static Point[] readPoints() {
        Point A[] = new Point[1000];
        Scanner input = null;
        try {
            input = new Scanner(new File("points.txt"));
        } catch (Exception ex) {
            System.out.println("Could not open file.");
            System.exit(1);
        }

        for (int p = 0; p < 1000; p++) {
            double x = input.nextDouble();
            double y = input.nextDouble();
            A[p] = new Point(x,y);
        }

        return A;
    }

    /**
     * Compute the distance between two points (x1, y1) and (x2, y2)
     */
    public static double distance(Point one,Point two) {
        return Math.sqrt((two.x - one.x) * (two.x - one.x) + (two.y - one.y) * (two.y - one.y));
    }

    public static void main(String[] args) {
        Point points[] = readPoints();

        // p1 and p2 are the indices in the points array
        int p1 = 0, p2 = 1; // Initial two points
        double shortestDistance = distance(points[p1],points[p2]); // Initialize shortestDistance

        // Compute distance for every two points
        for (int i = 0; i < points.length; i++) {
            for (int j = i + 1; j < points.length; j++) {
                double distance = distance(points[i],points[j]); // Find distance

                if (shortestDistance > distance) {
                    p1 = i; // Update p1
                    p2 = j; // Update p2
                    shortestDistance = distance; // Update shortestDistance
                }
            }
        }

        // Display result
        System.out.println("The closest two points are "
                + "(" + points[p1].x + ", " + points[p1].y + ") and ("
                + points[p2].x + ", " + points[p2].y + ")");
    }

}

Here are some important differences to note about this code.

Adding a method to the class

Besides member variables and constructors, classes can also contain methods. To show an example of this, here is an updated version of the Point class that adds a method to the class.

public class Point {
    public double x;
    public double y;

    public Point(double x,double y) {
        this.x = x;
        this.y = y;
    }

    public void print() {
        System.out.print("("+x+","+y+")");
    }
}

I have added a print() method to the Point class to make it possible for Points to print themselves. Here are some things to notice about this method.

Once we have added the print() method to the Point class, we can rewrite the code in the main method that prints the result. To replace the original print statement we can now do this:

// Display result
System.out.print("The closest two points are ");
points[p1].print();
System.out.print(" and ");
points[p2].print();
System.out.println();

This code shows how you call a non-static method. To call such a method you have to start by identifying the object you want to call the method on. Next, you type a dot. After the dot you call the method you want to call. In the code above you can see us calling the print() method on a couple of the Point objects stored in the array of Points.