How to assign a string to an empty string variable - python

grade=""
name=[]
courseworkMark=[]
examMark=[]
file=open("Test Marks.csv","r")
for line in file:
LineFromFile=(line.strip())
pupilName,pupilCoursework,pupilExam=LineFromFile.split(",")
name.append(str(pupilName))
courseworkMark.append(int(pupilCoursework))
examMark.append(int(pupilExam))
file.close
#-----------------------------------------------------------------------------------------------------------------------------------------------------------
def calculatePercentage(courseworkMark, examMark):
Percentage = round(((courseworkMark[index]+examMark[index])/160)*100)
return Percentage
#-----------------------------------------------------------------------------------------------------------------------------------------------------------
def calculateGrade(Percentage):
if Percentage >= 70:
#print("Your grade is an A")
grade=="A"
elif Percentage >=60 and Percentage <=69:
#print("Your grade is a B")
grade=="B"
elif Percentage >=50 and Percentage <=59:
#print("Your grade is a C")
grade=="C"
elif Percentage >=45 and Percentage <=49:
#print("Your grade is a D")
grade=="D"
else:
#print("You have failed")
grade=="Fail"
#-----------------------------------------------------------------------------------------------------------------------------------------------------------
def displayInformation(name,Percentage):
print(name[index],"got",Percentage,"% in total which is a/an",grade)
#-----------------------------------------------------------------------------------------------------------------------------------------------------------
for index in range (len(name)):
Percentage = calculatePercentage(courseworkMark, examMark)
Grade = calculateGrade(Percentage)
displayInformation(name, Percentage)
Hi everyone, I am currently trying to assign another string to an already existing empty string variable however when I run the code, the value for grade is still empty as it is when first defined, I hope someone is able to help, many thanks

I see three problems.
You compare grade with strings instead of assigning: "==" instead of "="
You assign value to variable Grade, not grade.
calculateGrade returns nothing.

Related

Python program to calculate average quiz grade for students

Ok, it I don't understand where I am going wrong because I had help with this coding and for the person who originally wrote it, it works just fine. However, mine seems to be malfunctioning. It keeps displaying the 'highest grade' multiple times instead of just once like it's supposed to. Having some real newbie problems here.
This is the code:
#this program will compute average quiz grade for a group of 5 students
#prompt user for quiz grade using a for loop for each of the 5 students
#assign names to student list
students = ["John", "Jake", "Jane", "Sally", "Susie"]
#grades: 90-100=A, 80-90=B, 70-80=C, 60-70=D, <60=F
#prompt user for student grades
grades = []
for student in students:
grade = eval(input(f"Enter the grade for {student}: "))
grades.append(grade)
sum = 0
for i in range(0,5):
for i in grades:
sum+=i
avg_grade=sum/5
#print average grade of students
if(avg_grade >=90):
print("Average Grade: A")
elif(avg_grade>=80 and avg_grade<90):
print("Average Grade: B")
elif(avg_grade>=70 and avg_grade<80):
print("Average Grade: C")
elif(avg_grade>=60 and avg_grade<70):
print("Average Grade: D")
else:
print("Average Grade: F")
#print highest grade
max_grade=max(grades)
for i in grades:
if(max_grade>=90):
print("Highest Grade: A")
elif(max_grade>=80 & max_grade<90):
print("Highest Grade: B")
elif(max_grade>=70 & max_grade<80):
print("Highest Grade: C")
elif(max_grade>=60 & max_grade<70):
print("Highest Grade: D")
else:
print("Highest Grade: F")
You are using a for loop at the end, which means for every single grade, the highest grade will be printed out.
You can delete the for, and unindent the if, elif, and else statements. Then the program should work as intended.
First of all, instead of using a variable such as sum, because sum is a python special function, you should use something like total.
Second, you shouldn't be using eval(input()) because the eval does nothing.
Third, when doing the for loop, you don't already know the number of students so it should be for i in range(len(students)-1) and the -1 part because list indexing starts at 0. Also, the second for loop should use a different variable then i because i is already used, so use something like j.
Use just sum to get the total grade and average value. Don't need to run an additional loop for 5 times.
total = sum(grades)
avg_grade = total/len(grades)
Then you don't need to run a loop to get the highest grade and also else should be indented with like other if elif. Follow the code
students = ["John", "Jake", "Jane", "Sally", "Susie"]
grades = []
for student in students:
grade = eval(input(f"Enter the grade for {student}: "))
grades.append(grade)
total = sum(grades)
avg_grade = total/len(grades)
if(avg_grade >= 90):
print("Average Grade: A")
elif(avg_grade >= 80 and avg_grade < 90):
print("Average Grade: B")
elif(avg_grade >= 70 and avg_grade < 80):
print("Average Grade: C")
elif(avg_grade >= 60 and avg_grade < 70):
print("Average Grade: D")
else:
print("Average Grade: F")
max_grade = max(grades)
if(max_grade >= 90):
print("Highest Grade: A")
elif(max_grade >= 80 & max_grade < 90):
print("Highest Grade: B")
elif(max_grade >= 70 & max_grade < 80):
print("Highest Grade: C")
elif(max_grade >= 60 & max_grade < 70):
print("Highest Grade: D")
else:
print("Highest Grade: F")
sum = 0
for i in range(0,5):
for i in grades:
sum+=i
avg_grade=sum/5
what that does is essentially go through every grade and increment sum every time and do that 5 times. It's unnecessarily O(n^2) and will run significantly slower when you add a lot of data.
Other than that a couple of useful things were pointed out by the other answers, I think one of them directly put the code there too so there isn't much I can say.
Basically you had logical flaws in your code that caused it to not function as intended.
debugging:
as you can see above the values for sum and avg_grade are totally not what they're intended to be, this was uncovered using print statements in the right places.
Your logic in implementation was flawed for the next part too, but this post is already too wordy for it's purpose.

Why is each grade inputted the same no matter what the program defines including the average?

The program is as follows: Write a program that asks the user to input 5 test scores. The program should display a letter grade for each score and the average test score.
I am having issues with my output showing me a letter grade of the first inputted grade for every grade including the average. My numeric average is also being outputted as a letter grade, but it gives the correct average letter for that rather than the correct numeric result for the grade. I am in a low level coding class, therefore the program must be written in this format.
Here is the code:
a=float(input("Enter score 1:"))
b=float(input("Enter score 2:"))
c=float(input("Enter score 3:"))
d=float(input("Enter score 4:"))
e=float(input("Enter score 5:"))
def determine_grade(a,b,c,d,e):
num=a
if(num<=100 and num>=90):
grade='A'
elif(num<=89 and num>=80):
grade='B'
elif(num<=79 and num>=70):
grade='C'
elif(num<=69 and num>=60):
grade='D'
else:
grade='F'
return grade
def calc_average(a,b,c,d,e):
mean=(a+b+c+d+e)//5
if mean<=100 and mean>=90:
avggrade='A'
elif(mean<=89 and mean>=80):
avggrade='B'
elif(mean<=79 and mean>=70):
avggrade='C'
elif(mean<=69 and mean>=60):
avggrade='D'
else:
avggrade='F'
return avggrade
grade=determine_grade(a,b,c,d,e)
avggrade=determine_grade(a,b,c,d,e)
mean=calc_average(a,b,c,d,e)
determine_grade(a,b,c,d,e)
calc_average(a,b,c,d,e)
print("Score Numeric Grade Letter Grade")
print("--------------------------------------------")
print("Score 1: ",a," ",grade)
print("Score 2: ",b," ",grade)
print("Score 3: ",c," ",grade)
print("Score 4: ",d," ",grade)
print("Score 5: ",e," ",grade)
print("--------------------------------------------")
print("Average Score: ",mean," ",avggrade)
Whenever I put in (a):
num=a,b,c,d,e
in place of what is shown in the code, I get a syntax error saying:
TypeError: '<=' not supported between instances of 'tuple' and 'int'
If I don't do what has been shown in (a), my output is this:
Enter score 1:90
Enter score 2:88
Enter score 3:76
Enter score 4:68
Enter score 5:40
Score Numeric Grade Letter Grade
--------------------------------------------
Score 1: 90.0 A
Score 2: 88.0 A
Score 3: 76.0 A
Score 4: 68.0 A
Score 5: 40.0 A
--------------------------------------------
Average Score: C A
Okay, so there's some things to talk about here. First, I suggest that you experiment a bit more with simpler functions to properly get used to them. When you define determine_grade(a,b,c,d,e) your function will expect to find a,b,c,d,e arguments inside the function, but if you read it again, you'll notice that you only mention a. This means when you call grade=determine_grade(a,b,c,d,e) you're only calculating a's grade, and that's why you have the same grade for everyone (if you type grade with your code you'll notice it will output 'A'.
Another way to write a function that does exactly what you're looking for is this:
def determine_grade(score):
num=score
if(num<=100 and num>=90):
grade='A'
elif(num<=89 and num>=80):
grade='B'
elif(num<=79 and num>=70):
grade='C'
elif(num<=69 and num>=60):
grade='D'
else:
grade='F'
return grade
You input a score (that can be a,b,c,d or e) and it calculates a grade. If you want to get everyone's grade, then you can do something like this:
grades=[]
for i in [a,b,c,d,e]:
grades.append(determine_grade(i))
This will bring a list with all grades.
Then, if you want the average grade, it's better to calculate the average score, so you can use your same function to get the grade:
mean_score=np.array([a,b,c]).mean()
mean_grade(determine_grade(mean_score)
Doing this you'll have all the information you need with way less lines of code (And you can make it even more efficient using list comprehensions, but that's a bit more advanced).
To answer your question, your functions should be rewritten to accept a single input and then called several times. Also, your program is a classic case of something that should be DRYed up (Don't Repeat Yourself). Instead of manually typing a = input(), b = input() why not consider just tossing all these inputs into a list (perhaps with some string formatting on your prompt like my code). Below is a program that can easily be adjusted to accept arbitrary amounts of inputs:
input_scores = [] # make our list
scores_input = 5 # tell the program we have 5 scores to record
for input_count in range(1, scores_input + 1):
input_scores.append(float(input("Enter score {}:".format(input_count))))
def determine_grade(percent): # single input
if 90 <= percent <= 100:
grade = 'A'
elif 80 <= percent <= 89:
grade = 'B'
elif 70 <= percent <= 79:
grade = 'C'
elif 60 <= percent <= 69:
grade = 'D'
else:
grade = 'F'
return grade # single output
def calc_average(local_score_list): # expects the list we made earlier (many inputs)
mean = sum(local_score_list) // len(local_score_list)
if 90 <= mean <= 100:
average_grade = 'A'
elif 80 <= mean <= 89:
average_grade = 'B'
elif 70 <= mean <= 79:
average_grade = 'C'
elif 60 <= mean <= 69:
average_grade = 'D'
else:
average_grade = 'F'
return mean, average_grade # have our function return both values, since it calculated them both anyways
compiled_scores = []
for test_score in input_scores:
letter_grade = determine_grade(test_score) # calling our single input/output function many times in a for loop
compiled_scores.append((test_score, letter_grade)) # creating a tuple so each letter and percent is stored together
mean_percent, mean_letter_grade = calc_average(input_scores) # decompile both values from our function
print("Score Numeric Grade Letter Grade")
print("--------------------------------------------")
# now we iterate through all the scores made and print them
for count, result_tuple in enumerate(compiled_scores, 1): # just print the scores in a loop
print("Score {}: ".format(count), result_tuple[0], " ", result_tuple[1])
print("--------------------------------------------")
print("Average Score: ", mean_percent, " ", mean_letter_grade)
You can see that we condensed our input() lines -> a single line, and condensed the print statements as well! Now our program can take, say, 30 scores and work just as well!!! (This is huge)!! And all that is required to change is the number 5 at the top of our script -> 30. No longer will we have to type print('this') or input('that')! Our script will automatically adjust because we made it able to scale with our list.
My test case (using same numbers from your post):
Enter score 1:90
Enter score 2:88
Enter score 3:76
Enter score 4:68
Enter score 5:40
Score Numeric Grade Letter Grade
--------------------------------------------
Score 1: 90.0 A
Score 2: 88.0 B
Score 3: 76.0 C
Score 4: 68.0 D
Score 5: 40.0 F
--------------------------------------------
Average Score: 72.4 C
Let me know if you need further clarification on something I posted!

Simple Python code to assign corresponding letter to number grade

I am trying to write code so a user can input raw data that will pull up a numerical grade from a list, AND pair that numerical value with a letter grade. ie: the fourth grade in the list is 86, so it will PRINT 86 as well as the letter grade B.
Here is what I have so far:
grades = ['62','68','93','75','89','85']
print grades [3]
def lettergrade (grades):
if grades >=90:
print('A')
elif grades >=80 and grades <90:
print('B')
elif grades >=70 and grades <80:
print('C')
elif grades >=60 and grades <70:
print('D')
else:
print('F')
print lettergrade (grades)
This should achieve what you are looking for:
grades = [62, 68, 93, 75, 89, 85]
def LetterGrade(grade):
if grade >= 90:
result = [grade, 'A']
elif grade >= 80 and grades < 90:
result = [grade, 'B']
elif grade >= 70 and grades < 80:
result = [grade, 'C']
elif grade >= 60 and grades < 70:
result = [grade, 'D']
else:
result = [grade, 'F']
return result
# call LetterGrade for each value in grades array
for grade in grades:
print(LetterGrade(grade))
You needed to loop for each value in the grades array. Also, try to get into the habit of following PEP 8 (Python style guide)
I am confused here, If you want the user input why do you want a list of values then? all you have to do is to wait for user input and check which grade that input belongs too. Please comment If you want some changes!!
x = raw_input("Enter Score: ")
score = float(x)
try:
if grades >=90:
print('A', score)
elif grades >=80 and grades <90:
print('B', score)
elif grades >=70 and grades <80:
print('C', score)
elif grades >=60 and grades <70:
print('D', score)
else:
print('F', score)
except:
print "Error"
The problem that you are experiencing is grades contains only Strings. '1' is a String just like 'hello'. In python, Strings will not be equal to numbers, so comparing them will always be false. In addition, you are comparing the entirety of grades to a number, which will also evaluate to false. The comparison that you are looking for is if(grades[index]>= 90): where index is whatever index you are looking at.
The print() statement inside lettergrade() will only print out the grade, so change each print statement to `print('LETTER:' + value).
In addition, the method lettergrade() will only print out one thing, so there needs to be a loop to call it multiple times, with multiple values:
for value in grades:
lettergrade(value)
You need to be careful with indentation, python is a language indented.
Try this:
# define lettergrade function
def lettergrade(grades):
if grades >=90:
return('A')
elif grades >=80 and grades <90:
return('B')
elif grades >=70 and grades <80:
return('C')
elif grades >=60 and grades <70:
return('D')
else:
return('F')
grades = ['62','68','93','75','89','85']
for grade in grades: # iterate in grades
# call to lettergrade function -> lettergrade(grade)
print(grade, ' equivalent ', lettergrade(grade))

Python 3- assigns grades [duplicate]

This question already has answers here:
Python 3- Assign grade
(2 answers)
Closed 6 years ago.
• Define a function to prompt the user to enter valid scores until they enter a sentinel value -999. Have this function both create and return a list of these scores. Do not store -999 in the list!
• Have main( ) then pass this the list to a second function which traverses the list of scores printing them along with their appropriate grade.
I am having trouble with the getGrade function, it gives the error for i in grades: name 'grades' is not defined.
def main():
grade = getScore()
print(getGrade(grade))
def getScore():
grades = []
score = int(input("Enter grades (-999 ends): "))
while score != -999:
grades.append(score)
score = int(input("Enter grades (-999 ends): "))
return grades
def getGrade(score):
best = 100
for i in grades:
if score >= best - 10:
print(" is an A")
elif score >= best - 20:
print(score, " is a B")
elif score >= best - 30:
print(score, " is a C")
elif score >= best - 40:
print(score, " is a D")
else:
print(score, "is a F")
main()
You defined your function to be getScore() but you're calling getScores(), so as would be expected this throws an error because the function you're calling doesn't actually exist / hasn't been defined.
Addendum: Since you changed your question, after fixing the previous error.
Likewise you're calling grades, but grades is defined in your other function not within the scope of the function where you're trying to iterate over grades.

How do you structure a recursive function?

I'm trying to create a recursive function that checks if a grade can be converted to a float, then checks to make sure the grade is between 0 and 100. My logic as to why this would work is:
Checks to see if the grade can be converted to a float.
If it can't be converted into a float, the user receives an error message, has to input a new grade, and gradeChecker checks again.
If it can be converted into a float, gradeChecker checks to see if it's between 0 and 100
If the grade between 0 and 100, the grade is then appended to the Assignments dictionary.
If the grade isn't between 0 and 100, the user gives a new grade, which is passed back in to the function, so repeat starting at step 1.
Can you tell me how this code doesn't follow that logic?
def gradeChecker(grade):
while True:
try:
grade = float(grade)
while (grade < 0) or (grade > 100):
print("Sorry, your grade must be between 0 and 100.")
grade = input("What grade did you receive on: %s? " % assignment)
gradeChecker(grade)
except:
print("Sorry, that's an invalid input. Please only use numbers and decimal points!")
grade = input("What grade did you receive on: %s? " % assignment)
else:
break
Assignments[assignment].append(grade)
Edit: Indentations fixed!
For reference, here is the entirety of the code I am using to pass grade into gradeChecker.
import collections #We import collections so we can use an ordered dictionary
Assignments = collections.OrderedDict() #We create an ordered dictionary called 'Assignments'
#We have to add each assignment to our dictionary individually because it's an ordered dictionary
#You can't convert a regular dictionary, which is unordered, to an ordered dictionary
#If you used a regular dictionary, when looping through the assignments they would be displayed at random
Assignments['Exam 1'] = [0.2] #We add the assignment and the weight to the dictionary
Assignments['Exam 2'] = [0.2] #We add the assignment and the weight to the dictionary
Assignments['Exam 3'] = [0.2] #We add the assignment and the weight to the dictionary
Assignments['Homework'] = [0.2] #We add the assignment and the weight to the dictionary
Assignments['LQR'] = [0.1] #We add the assignment and the weight to the dictionary
Assignments['Final'] = [0.1] #We add the assignment and the weight to the dictionary
#We have to define our grade checker before it is called so that it can be used to verify users inputs
def gradeChecker(grade): #Used to verify that a users grades are in-between 0 and 100
while True:
try:
grade = float(grade)
while (grade < 0) or (grade > 100):
print("Sorry, your grade must be between 0 and 100.")
grade = input("What grade did you receive on: %s? " % assignment)
gradeChecker(grade)
except:
print("Sorry, that's an invalid input. Please only use numbers and decimal points!")
grade = input("What grade did you receive on: %s? " % assignment)
else:
break
Assignments[assignment].append(grade) #We append the grade to the assignment to be used with it's weight for the final grade calculation
#INPUT
for assignment in Assignments.keys(): #We loop through every assignment in our Assignments dictionary
grade = input("What grade did you receive on: %s? " % assignment) #We ask the user to enter their grade
gradeChecker(grade) #We check to see if their grade is valid by passing their input through the gradeChecker function
Using both recursion and loop here is redundant. Moreover, loops should be preferred to recursion in 'normal' languages like Python (i.e., not Lisp) unless you're dealing with an inherently recursive data structure like a tree.
Given that you never stated why you need to use recursion in the first place, I suggest to use something like this:
def input_grade(assignment):
while True:
try:
grade = input("What grade did you receive on: %s? " % assignment)
grade = float(grade)
if grade < 0 or grade > 1000:
raise ValueError
return grade
except:
print("Sorry, that's an invalid input. Please only use numbers and decimal points!")
for assignment in Assignments:
Assignments[assignment].append(input_grade(assignment))
Note 1. I didn't test the code above, but it should give you the general idea of how to structure this function.
Note 2. You should avoid modifying Assignments in the function, that's an unwanted side effect. Better offload this to the main code.
Note 3. Technically, the try..except in my code is an example of exception-based logic, which isn't a great thing (however, this is way better than using recursion here).
def gradeChecker(grade):
try:
grade = float(grade)
while (grade < 0) or (grade > 100):
print("Sorry, your grade must be between 0 and 100.")
grade = input("What grade did you receive on: %s? " % assignment)
gradeChecker(grade)
except:
print("Sorry, that's an invalid input. Please only use numbers and decimal points!")
grade = input("What grade did you receive on: %s? " % assignment)
else:
Assignments[assignment].append(grade)
the thing with your code is that it's redundant; the while statement is there to do what you already have the recursive calls doing. imo, the while statement is better since recursion often uses up more memory but thats just an opinion.

Categories

Resources