-3

I was working on following problem . But cant get any healthy logic.

1.There are number of students. For every student roll (unique), name is to be stored. For each subject, subject code and name is to be stored. A student can opt for number of subjects. System should be able to maintain student list, subject list and will be able to answer: i) which student has selected which subjects and ii) for a subject who are the students.

I Tried some logic but now I'm lost. Can anyone give me slightest idea how to proceed. am i approaching it in right way or any other good approach which you can suggest.

#include <iostream>
#include <string.h>
class StudentDetails {
public:
    int roll;
    char name1[15];
};
class SubjectDetails : public StudentDetails {
public:
    SubjectDetails() = default;
    SubjectDetails(int n, string naam)
        : code(n)
        , name(naam)
    {
    }
    int code;
    string name2;
};
class Subject {
    SubjectDetails s1{ 1, "A" };
    SubjectDetails s2{ 2, "B" };
    SubjectDetails s3{ 3, "C" };
    SubjectDetails s4{ 4, "D" };
    SubjectDetails s5{ 5, "E" };
};
class Student {
public:
    Subject s[5]
};
  • Why will you use inheritance? – Nathan Xabedi Sep 20 '19 at 16:51
  • What else i can do . any idea ? –  Sep 20 '19 at 16:52
  • 1
    A rule of thumb: inheritance follows the "is-a" relationship, and composition (contains) follows the "has-a" rule. For example, a `Student` *has-a* name; A `Student` is *not* a name, so the `Student` contains a name member and does not inherit the name class. – Thomas Matthews Sep 20 '19 at 17:00
  • Use `std::string`. It can dynamically grow. A character array is fixed length and usually is too large or too small. You have to reallocate the array to make it bigger. Similarly with arrays and `std::vector`. – Thomas Matthews Sep 20 '19 at 17:02
  • There are many ways to organize the data. For example, you could make separate tables according to [Database Normal Forms](https://en.wikipedia.org/wiki/Database_normalization). – Thomas Matthews Sep 20 '19 at 17:05
  • Another idea is to have a database of `Student`. Add methods to the `Student` class to add or remove `Subject`s. The `Student` class may want methods to search the `Subject` database. – Thomas Matthews Sep 20 '19 at 17:07
  • Could you add to your question an explanation of why you did what you did? Why did you choose this approach? What makes it a good representation of the situation you are modeling? – JaMiT Sep 20 '19 at 17:54

1 Answers1

2

You are likely having problems because this is not a good way to use inheritance. Inrheritance establishes an Is-A relationship between two objects.

Recommended reading: Liskov Substitution Principle.

In this case SubjectDetails is a StudentDetails and must be usable anywhere you would use a StudentDetails. If you have a list of StudentDetails, inheritance says you can insert a SubjectDetails into it.

What you want is a Has-A relationship. A Student Has-A Subject. A Subject Has-A name. A Subject Has-A code. In your case a Subject can have many names and many codes. From the problem description in the question,

For each subject, subject code and name is to be stored.

I do not believe this makes sense. I suggest eliminating SubjectDetails and incorporating it in Subject. Side note, any time you find yourself making sequentially numbered variables, you likely really want an array.

class Subject {
public:
    Subject() = default;
    Subject(int n, string naam)
        : code(n)
        , name(naam)
    {
    }
    int code;
    string name;
};

Similarly Students may have many names, but should only have one Roll. Names are generally stacked up according to cultural norms (John Jacob Jingleheimer-Shmidt, for example packs the names together into one larger name) so StudentDetails should also be rolled into Student and discarded.

class Student {
public:
    int roll;
    char name1[15];
    int number_subjects;
    Subject subjects[5]; // use descriptive names. s tells you nothing about the purpose 
                         // of the member, and this often slows debugging and reading
};

Now Students have rolls, names, and up to five subjects. Consider using a std::vector<Subjects> instead of the array if the maximum number of subjects is unknown and vector is permitted for use in the assignment. It makes keeping track of a dynamic list of subjects much easier.

Finding the subjects per student is easy. Student object tells you outright with the subjects member.

To find the students in a subject you have to do some work. Either You search through a list of students for all Students that contain a given Subject, a simple-but-slow task, or you maintain a second list that maps Subjects to a list of Students. The mapping table makes look-up very fast, but maintaining the integrity of the mapping table as students and subjects are added and removed can be very hard.

Which one you select depends on the expected access pattern (if looking up students by subject is common and adding students and subjects is not, maintaining the extra subject->student mapping may be an important optimization), the amount of resources available, and how much time you have remaining to complete the assignment.

user4581301
  • 33,082
  • 7
  • 33
  • 54