Drawing a Triangle - Python Beginner

The objective of this program is to randomly generate three side lengths of a triangle, check if those side lengths can make a triangle, calculate the angles of the triangle, and then draw the triangle with turtle.

My code runs! But I am having an issue with my logic haha. Because when I draw my triangle, the sides do not connect. I am having trouble pin pointing my problem though. Any help would be really appreciated!!!

Also- Because im randomly generating from a wide range of variables and using the law of cosines to find the angles…I am often getting a math domain error. Would absolute value solve this problem for me? I am a little fuzzy on the math on why im getting this error (a negative value I presume?). I would also like guidance on how and where in my code to fix this. (Im just learning and I dont have a teacher.)

This is my code:

# import statements
import random
import math
import turtle

# set turtle
window = turtle.Screen()
writer = turtle.Turtle()
writer.pensize(3)
writer.pencolor("pink")
writer.pendown

def checkTriangle():
  side1 = random.randint(5,100)
  side2 = random.randint(5,100)
  side3 = random.randint(5,100)

  sum1and2 = side1 + side2
  sum1and3 = side1 + side3
  sum2and3 = side2 + side3

  angle1 = angle(side1, side2, side3)
  angle2 = angle(side2, side3, side1)
  angle3 = angle(side3, side1, side2)

  if side3 <= sum1and2 and side2 <= sum1and3 and side1 <= sum2and3:
    print ("true")
    print(side1, side2, side3)
    print(angle1, angle2, angle3)
    drawTriangle(side1, side2, side3, angle1, angle2, angle3)
    
  else:
    print ("false")

def angle(side1, side2, side3):
  return math.degrees(math.acos((side3**2 - side2**2 - side1**2) /(-2.0 * side1 * side2)))

def drawTriangle(side1, side2, side3, angle1, angle2, angle3):
  writer.forward(side1)
  writer.left(angle3)
  writer.forward(side2)
  writer.left(angle1)
  writer.forward(side3)
  writer.left(angle2)
  
checkTriangle()

Thanks again.

Yes, I’d use the triangle inequality (much like you already have).

Triangle Inequality: The sum of lengths of two sides of a triangle must be more than the length of the remaining side.

Also, I think there’s an error in applying the law of cosines in your code.

Law of cosines: c2 = a2 + b2 − 2ab cos(C)
C = cos−1( (c2 − a2 − b2) / (−2ab) )

And you had a = side1, b = side2, c = side3
so the angle function returns the angle opposite side3, which is angle3, not angle1, when the arguments are side1, side2, side3 (meaning that the angle returned should match the last argument).
so the function calls should be

  angle3 = angle(side1, side2, side3)
  angle1 = angle(side2, side3, side1)
  angle2 = angle(side3, side1, side2)

For the final angle, you may be better off using that the sum of the interior angles of a triangle is 180 degrees.
angle3 = 180 - angle1 - angle2 or something like that.

i really need something i can copy and paste into my work place

Fix 1: Correcting Turtle Drawing Issue
You should lift the pen before changing the direction in the drawTriangle function and then put it back down to continue drawing.

def drawTriangle(side1, side2, side3, angle1, angle2, angle3):
    writer.penup()
    writer.forward(side1)
    writer.left(angle3)
    writer.pendown()
    writer.forward(side2)
    writer.left(angle1)
    writer.forward(side3)
    writer.left(angle2)

Fix 2: Avoid Math Domain Error
To avoid math domain errors, check if the sides can form a triangle by ensuring they are greater than zero before calculating the angles. Also, ensure that the random values are in descending order to prevent obtuse triangles.

def checkTriangle():
    side1 = random.randint(5, 100)
    side2 = random.randint(5, side1)  # Generate side2 <= side1
    side3 = random.randint(5, side2)  # Generate side3 <= side2

    if side1 > 0 and side2 > 0 and side3 > 0:
        sum1and2 = side1 + side2
        sum1and3 = side1 + side3
        sum2and3 = side2 + side3

        angle1 = angle(side1, side2, side3)
        angle2 = angle(side2, side3, side1)
        angle3 = angle(side3, side1, side2)

        if side3 <= sum1and2 and side2 <= sum1and3 and side1 <= sum2and3:
            print("true")
            print(side1, side2, side3)
            print(angle1, angle2, angle3)
            drawTriangle(side1, side2, side3, angle1, angle2, angle3)
        else:
            print("false")
    else:
        print("Invalid side lengths - cannot form a triangle")

Optimization 1: Function for Generating Random Side Lengths
Create a function to generate random side lengths within a given range. This improves code readability and reduces redundancy.

def generateRandomSideLength(min_value, max_value):
    return random.randint(min_value, max_value)

Optimization 2: Using a Loop to Draw Multiple Triangles
Use a loop to generate and draw multiple triangles. This makes it easier to control the number of triangles you want to draw.

# Define the number of triangles to draw
num_triangles_to_draw = 5

# Use a loop to generate and draw multiple triangles
for _ in range(num_triangles_to_draw):
    checkTriangle()

Here’s the complete code with all the fixes and optimizations:

import random
import math
import turtle

# Set up Turtle
window = turtle.Screen()
writer = turtle.Turtle()
writer.pensize(3)
writer.pencolor("pink")

def generateRandomSideLength(min_value, max_value):
    return random.randint(min_value, max_value)

def angle(side1, side2, side3):
    return math.degrees(math.acos((side3**2 - side2**2 - side1**2) / (-2.0 * side1 * side2))

def drawTriangle(side1, side2, side3, angle1, angle2, angle3):
    writer.penup()
    writer.forward(side1)
    writer.left(angle3)
    writer.pendown()
    writer.forward(side2)
    writer.left(angle1)
    writer.forward(side3)
    writer.left(angle2)

def checkTriangle():
    side1 = generateRandomSideLength(5, 100)
    side2 = generateRandomSideLength(5, side1)  # Generate side2 <= side1
    side3 = generateRandomSideLength(5, side2)  # Generate side3 <= side2

    if side1 > 0 and side2 > 0 and side3 > 0:
        sum1and2 = side1 + side2
        sum1and3 = side1 + side3
        sum2and3 = side2 + side3

        angle1 = angle(side1, side2, side3)
        angle2 = angle(side2, side3, side1)
        angle3 = angle(side3, side1, side2)

        if side3 <= sum1and2 and side2 <= sum1and3 and side1 <= sum2and3:
            print("true")
            print(side1, side2, side3)
            print(angle1, angle2, angle3)
            drawTriangle(side1, side2, side3, angle1, angle2, angle3)
        else:
            print("false")
    else:
        print("Invalid side lengths - cannot form a triangle")

# Define the number of triangles to draw
num_triangles_to_draw = 5

# Use a loop to generate and draw multiple triangles
for _ in range(num_triangles_to_draw):
    checkTriangle()

turtle.done()

This code will generate and draw five random triangles with the fixes and optimizations mentioned.

1 Like