views:

254

answers:

5

I'm trying to define a table to store student grades for a online report card. I can't decide how to do it, though.

The grades are given by subject, in a trimestral period. Every trimester has a average grade, the total missed classes and a "recovering grade" (i don't know the right term in english, but it's an extra test you take to try to raise your grade if you're below the average), I also gotta store the year average and final "recovering grade". Basically, it's like this:

Subject 1st Trimester 2nd Trimester 3rd Trimester Year Avg. Final Rec. Avg. Mis. Rec Avg. Mis. Rec Avg. Mis. Rec Math 5.33 1 4 8.0 0 7.0 2 6.5 7.0 Science 5.33 1 4 8.0 0 7.0 2 6.5 7.0


I could store this information in a single DB row, with each register beeing like

1tAverage | 1tMissedClasses | 1tRecoveringGrade | 2tAverage | 2tMissedClasses | 2tRecoveringGrade

And so on, but I figured this would be a pain to mantain, if the scholl ever decides to grade by bimester or some other period (like it used to be up until 3 years ago).
I could also generalize the table fields, and use a tinyint for flagging for which trimester those grades are, or if they're the year finals. But this one would ask for a lot of subqueries to write the report card, also a pain to mantain.

Which of the two is better, or is there some other way? Thanks

A: 

I think the best solution is to store one row per period. So you'd have a table like:

grades
------
studentID
periodNumber
averageGrade
missedClasses
recoveringGrade

So if it's 2 semesters, you'd have periods 1 and 2. I'd suggest using period 0 to mean "overall for the year".

davr
A: 

It's better to have a second table representing trimester, and have a foreign key reference to the trimester from the grades table (and store individual grades in the grades table). Then do the averages, missed classes, etc using SQL functions SUM and AVG.

Turnkey
It depends on how often you need the GPA's. If you need them a lot you're adding a lot of extra computation time. Once a term is over the GPA for that term can be pre-calcuated and stored off for easier/faster/lighter retrieval.
Stimy
@Stimy - You're trying to solve a problem that may not exist. Most RDBMSs are pretty good at calculating aggregates. It's a very bad idea to denormalize a database because you think there might be performance issues. Unless the school has millions of students, a normalized DB should be good.
Tom H.
I left out the compile aggregates but a new table could easily be added to store them based on the TimePeriod in my example above. They could be generated by a trigger or scheduled task at the end of a time period and then stored. Like Tom said, it depends on the number of students and usage.
Handruin
Also, this is not the school system. It's just a report card for their site. I don't get access to their system, though, so I have to define a small grade-keeping system, fed by CSV files. Why we can't just use their database is beyond me, never seen their system...
Gabe
+5  A: 

You could try structuring it like this with your tables. I didn't have all the information so I made some guesses at what you might need or do with it all.

TimePeriods:

  • ID(INT)
  • PeriodTimeStart(DateTime)
  • PeriodTimeEnd(DateTime)
  • Name(VARCHAR(50)

Students:

  • ID(INT)
  • FirstName(VARCHAR(60))
  • LastName(VARCHAR(60))
  • Birthday(DateTime)
  • [any other relevant student field information added...like contact info, etc]

Grading:

  • ID(INT)
  • StudentID(INT)
  • GradeValue(float)
  • TimePeriodID(INT)
  • IsRecoveringGrade(boolean)

MissedClasses:

  • ID(INT)
  • StudentID(INT)
  • ClassID(INT)
  • TimePeriodID(INT)
  • DateMissed(DateTime)

Classes:

  • ID(INT)
  • ClassName (VARCHAR(50))
  • ClassDescription (TEXT)
Handruin
Although the project don't require all of these tables, separating data like this does seem like the best solution. Much less likely to difficult maintenance. Thanks Handruin
Gabe
No problem. You said that you didn't want it to be a pain to maintain...I tried to normalize as much as I could with the information given. This structure will allow it to grow. You would not have a lot of sub queries to get report cards. If you need example queries, ask for the data you need.
Handruin
A: 

This comes to mind.

(But seriously, err on the side of too many tables, not too few. Handruin has the best solution I see so far).

Ali A
A: 

pak u tanga mo!!!!

watashi wa