Reputation: 11
blueprint = [[1,"A"], [2,"C"], [3,"B"], [4,"D"], [5,"A"], [6,"A"], [7,"B"], [8,"A"], [9,"C"], [10,"A"], [11,"D"], [12,"A"], [13,"C"], [14,"C"]
,[15,"B"], [16,"A"], [17,"B"], [18,"A"], [19,"C"], [20,"D"]]
def check_answer(students_answer):
points = 0
total = 20
if students_answer[0]==blueprint[0][1]:
points =+ 1
elif students_answer[1]==blueprint[1][1]:
points =+ 1
#etc.
else:
points =+ 0
score = (points*100)/(total)
return score
print(check_answer(["A", "C"]))
Why doesn't my function calculate the % of right answers for longer than answer 1, which is "A"?
Upvotes: 0
Views: 67
Reputation: 1300
Why doesn't my function calculate the % of right answers for longer than answer 1, which is "A"?
Let's take a look at your data & function
# data
blueprint = [[1,"A"], [2,"C"], [3,"B"], [4,"D"], [5,"A"], [6,"A"], [7,"B"], [8,"A"], [9,"C"], [10,"A"], [11,"D"], [12,"A"], [13,"C"], [14,"C"], [15,"B"], [16,"A"], [17,"B"], [18,"A"], [19,"C"], [20,"D"]]
# function call
print(check_answer(["A", "C"]))
first list in blueprint
is [1,"A"]
. the check_answer()
argument is ["A", "C"]
. When the line in the loop here runs, it found what it's looking for
if students_answer[0]==blueprint[0][1]: # students_answer[0] is "A", blueprint[0][1] is "A", too
points =+ 1
elif students_answer[1]==blueprint[1][1]:
points =+ 1
#etc.
that means it skips all the elifs & else, straight to calculating score
. That's why score only contains the first "A"
.
one approach you can do is to use zip(*blueprint)
to unpack the lists inside blueprint, into this
[(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20),
('A', 'C', 'B', 'D', 'A', 'A', 'B', 'A', 'C', 'A', 'D', 'A', 'C', 'C', 'B', 'A', 'B', 'A', 'C', 'D')]
then loop on that to count the grades.
so,
scorelist = list(zip(*blueprint))
total = len(scorelist[1])
answer_list = ["A", "C"]
first_a, second_a = answer_list
points = 0
for sc in scorelist[1]:
if sc == first_a or sc == second_a:
points += 1
score = (points*100)/(total)
print(score)
or you can even just joined all the scores strings & use str.count()
joined_scores = ''.join(scorelist[1])
print(joined_scores)
# 'ACBDAABACADACCBABACD'
points = joined_scores.count(first_a) + joined_scores.count(second_a)
print(points*100/total)
# 65.0
Upvotes: 1
Reputation: 106465
The first items in the tuples in your blueprint
list are redundant because they are simply the indices of their respective tuples plus one. You should make it a simple list of strings instead:
blueprint = ['A', 'C', 'B', 'D', 'A', 'A', 'B', 'A', 'C', 'A', 'D', 'A', 'C', 'C', 'B', 'A', 'B', 'A', 'C', 'D']
so that you can calculate the percentage of right answers in student_answer
with a zip of the two lists like this:
sum(1 for s, b in zip(student_answer, blueprint) if s == b) / len(student_answer) * 100
Upvotes: 1
Reputation: 140168
I don't get why you need to recall the list index in blueprint
but if the data are like this, you could just zip
the data together, unpack, and compare.
This way of doing it is really unefficient. What if you have 100 questions? will you copy/paste 100 times your (wrong) elif
statements?
Score 1 for success, 0 for fail, divide by total and multiply by 100, in a generator comprehension fed to sum
:
def check_answer(students_answer):
return 100*(sum(correct==attempt for (_,correct),attempt in zip(blueprint,students_answer))/len(blueprint))
Upvotes: 1