apprenda take home assessment
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

53 lines
1.5 KiB

  1. package rect
  2. import (
  3. "fmt"
  4. "math"
  5. )
  6. // line is described as two Points
  7. type line struct {
  8. pt1, pt2 Point
  9. }
  10. // determinants aids by calculating necessary values for performing
  11. // calculations using the determinant of two points
  12. func determinants(l line) (float64, float64, float64) {
  13. a := l.pt2.Y - l.pt1.Y
  14. b := l.pt1.X - l.pt2.X
  15. c := a*l.pt1.X + b*l.pt1.Y
  16. return a, b, c
  17. }
  18. // lineIntersection returns the Point of intersection between two lines.
  19. // lineIntersection will only return a point if the point lies on the
  20. // line, otherwise it will return a nil point and an error
  21. func lineIntersection(l1, l2 line) (Point, error) {
  22. a1, b1, c1 := determinants(l1)
  23. a2, b2, c2 := determinants(l2)
  24. det := a1*b2 - a2*b1
  25. if det != 0 {
  26. x := ((b2*c1 - b1*c2) / det)
  27. y := ((a1*c2 - a2*c1) / det)
  28. minx1, maxx1 := math.Min(l1.pt1.X, l1.pt2.X), math.Max(l1.pt1.X, l1.pt2.X)
  29. miny1, maxy1 := math.Min(l1.pt1.Y, l1.pt2.Y), math.Max(l1.pt1.Y, l1.pt2.Y)
  30. minx2, maxx2 := math.Min(l2.pt1.X, l2.pt2.X), math.Max(l2.pt1.X, l2.pt2.X)
  31. miny2, maxy2 := math.Min(l2.pt1.Y, l2.pt2.Y), math.Max(l2.pt1.Y, l2.pt2.Y)
  32. if minx1 <= x && x <= maxx1 && miny1 <= y && y <= maxy1 {
  33. if minx2 <= x && x <= maxx2 && miny2 <= y && y <= maxy2 {
  34. return Point{x, y}, nil
  35. }
  36. }
  37. }
  38. return Point{}, fmt.Errorf("lines do not intersect")
  39. }
  40. // lineOnLine determins if both points of a line, l1, are on the same line, l2
  41. func lineOnLine(l1, l2 line) bool {
  42. if onLine(l1.pt1, l1.pt2, l2.pt1) && onLine(l1.pt1, l1.pt2, l2.pt2) {
  43. return true
  44. }
  45. return false
  46. }