// Line segment

public final class Line {

   // instance variables
   final Point2D start, end;

   // constructors
   Line (final Point2D s, final Point2D e) { start=s; end=e; }
   Line (double startX, double startY, double endX, double endY) {
      this (new Point2D (startX, startY), new Point2D (endX, endY));
   }
   Line (final Point2D c) { this (new Point2D (0.0, 0.0), c); }

   // methods
   double length () { return start.distance (end); }

   Point2D intersects (final Line l) {
      final double den = (end.y-start.y)*(l.end.x-l.start.x)-
         (end.x-start.x)*(l.end.y - l.start.y);
      if (Math.abs(den) < 1.0E-10) throw new RuntimeException ("parallel lines");
      final double num = (end.y-start.y)*(start.x-l.start.x)-
         (end.x-start.x)*(start.y - l.start.y);
      final double iX = l.start.x + (l.end.x - l.start.x) * num / den;
      final double iY = l.start.y + (l.end.y - l.start.y) * num / den;
      return new Point2D (iX, iY);
   }

   // NB. "public" is necessary.
   @java.lang.Override // The annotation is recommended
   public String toString () {
      return String.format ("%s->%s)", start, end);
   }
}