CPSC 333: CRC Modeling: Application to an Example

Location: [CPSC 333] [Listing by Topic] [Listing by Date] [Previous Topic] [Next Topic] CRC Modeling Example


This material is a supplement for material that was presented during lectures on March 17, 1997.


Now, CRC modeling will be applied to an example.

This example will be somewhat incomplete (but consistent with the lab exercise and assignment problem), because we won't be modeling any classes except for those that would have been identified during requirements analysis. The changes that you'd need to make in order to make this more complete will be described briefly at the end.

Problem Statement

The system to be considered will be the final version of the Student Information System to be proposed. This version supports information about students, courses and course sections, and the grades that students can receive, and it provides a level of security: The system keeps track of the ``Registrars'' who can use this system, and the ``access level'' that each registrar has.

A class diagram for this system that shows ``problem domain'' classes, and structures and instance connections between them (but nothing else) is as follows.

Class Diagram for Student Information System

Creation of CRC Cards

We'll begin by creating a CRC card (or ``CRC index card'') for each of the classes shown on the above diagram, and filling in the information at the top of the card for each.

In order to do this, it will be necessary to try to identify the type and characteristics for each of the problem domain classes. There won't always be an obvious choice to make. For example, it might not be clear what the ``type'' should be for ``Course,'' ``Course Section,'' or ``Grade'' (and the choices made below might not be the best possible ones), but we'll simply make the best choices we can, for now.

That being said, here is the set of information that might be entered for the problem domain classes, on their CRC cards, at this point.

Class Name: Registrar
Class Type: Role
Class Characteristics: Tangible; sequential; persistent; guarded
Class Name: Student
Class Type: Role
Class Characteristics: Tangible; sequential; persistent; guarded
Class Name: Course
Class Type: Structure, Assembly, or Organizational Unit
Class Characteristics: Abstract; sequential; persistent; guarded
Class Name: Course Section
Class Type: Structure, Assembly, or Organizational Unit
Class Characteristics: Abstract, sequential; persistent; guarded
Class Name: Grade
Class Type: Property
Class Characteristics: Abstract; sequential; persistent; guarded

A few of the ``characteristics'' will likely be the same in all cases. It's likely that each ``problem domain'' class will contain data that we want to store between uses of the system, so it's likely that each problem domain class will be ``persistent.'' Since we aren't dealing with a multiple user system (in the sense that only one registrar can use the system at a time), and since this system isn't accessing or controlling multiple physical devices simultaneously, each problem domain class is also likely to be ``sequential.'' Finally, it's to be hoped that each class is ``guarded'' (at least, until we find good reason to open up access to the class's internal resources).

Events and Message Threads

In order to identify responsibilities and collaborators for each problem domain class, we will consider each of the events that this system will need to respond to.

Assumptions

Here are some assumptions that will affect many of the choices made below, that should be kept in mind.

While the above interface (and the information given above about its implementation) isn't really ``unrealistic'' (although the operations that are supported are probably a bit to simple), it should be noted that the process that's been followed to obtain it is incorrect. See CPSC 481 for a description of how human computer interface design should proceed.

Finally, you should bear in mind, when looking at the ``message threads'' given below, that these only show communication between problem domain objects. It's possible that complex computations are being performed ``within'' the classes without being messages being sent, as well.

Logging On and Off

Operations corresponding to the events (or requests)

are both the responsibilities of the ``Registrar'' class.

If a logon is successful, then the Registrar should send a message to the ``Task Manager'' described above, and the Task Manger should then send messages to all the other problem domain classes to request that their menus be displayed. Thus, ``Course'' class will have a responsibility, ``Create Courses Menu,'' the ``Course Section'' class will have a responsibility, ``Create Create Course Sections Menu,'' and so on. However, there won't be any direct communication between the ``Registrar'' class and other classes in order to cause menus to be displayed, so we won't show any (problem domain) collaborators for the responsibility ``Log On'' of ``Registrar,'' and the message thread for this operation will be trivial.

Similarly, Registrar will have a responsibility, ``Log Out,'' with a trivial message thread and no (problem domain) collaborators, but it will be necessary to add responsibilities ``Hide Courses Menu'' for ``Course,'' ``Hide Course Sections Menu'' for ``Course Section,'' etc..

We won't (explicitly) add ``Create Accounts Menu'' and ``Hide Accounts Menu'' as responsibilities for ``Registrar,'' because these will be part of the responsibilities ``Log On'' and ``Log Off,'' respectively.

Additional Responsibilities Involving the Interface

A similar interaction with the Task Manager will take place at the beginning and at the end of processing of every other command that can be selected using the menus: When a command has been selected, the class controlling the menu should send a message to the Task Manager, and then the Task Manager should send a message to all the other problem domain classes (possibly including the Registrar, this time), in order to request that the menus be disabled. On completion of the command, the class should send another message to the Task Manager, who will then send a message to all the other problem domain classes, requesting that their menus be enabled again.

Thus we'll also need to add responsibilities ``Enable Accounts Menu'' and ``Disable Accounts Menu'' for ``Registrar,'' ``Enable Courses Menu'' and ``Disable Courses Menu'' for ``Course,'' ``Enable Course Sections Menu'' and ``Disable Course Sections Menu'' for ``Course Section,'' and so on. None of these responsibilities have collaborators.

Operations on Registrars' Accounts

Operations corresponding to the requests

are all responsibilities of the class ``Registrar.'' It isn't necessary for this class to send messages to any others in order to perform these operations, so the message threads for these are all trivial, and none of these responsibilities for ``Registrar'' have any collaborators.

Operations on Courses

The operations corresponding to the requests

are all responsibilities of the class ``Course.'' Let's assume that the information returned on completion of the last two commands does not include information about course sections (and that a ``List Sections for Course'' will be provided by the system instead). In this case, it isn't necessary for ``Course'' to send any messages to complete these operations, so that none of the responsibilities have any collaborators and, again, all the message threads are trivial.

The operation

is also a responsibility of ``Course,'' but it's necessary for at least one message to be sent, in order for this operation to be performed.

In particular, let's assume that a course should not be deleted if any course sections for it still exist. In this case, the ``Course'' object (corresponding to the course that's to be deleted) should send a message, ``Get All Sections for Course,'' to the ``Course Section'' class. The ``Course Section'' class should return a sequence of ``section identifiers for course'' (terms, years, and section numbers) to the ``Course'' object. The object should complete the deletion if this sequence is empty, and should report the problem to the user and make no change otherwise.

The corresponding message thread is as follows.

Message Thread for ``Delete Course''

Because of this, ``Course Section'' should be listed as a collaborator, beside the responsibility ``Delete Course'' of ``Course,'' and ``Get All Sections for Course'' should be added as a responsibility of ``Course Section'' (with no collaborators).

Another ``message thread'' is possible for this operation, if the user is allowed to ``cancel'' operations: The user might choose to cancel the operation before a course has been identified. However, no messages would be sent at all in this case (so the message thread would be trivial), and no additional collaborators or responsibilities need to be added because of it.

This would all be a bit different if the system allowed a course to be deleted when course sections had been found: It would be necessary to delete the remaining course sections for the course at the same time, so that ``Course'' would send a message called ``Delete All Sections for Course,'' instead of ``Get All. In order to satisfy this request, ``Course Section'' would need to send a message to ``Grade,'' in order to check for (and, probably, eliminate) all the registrations and grades for students in the course sections that are about to disappear. This example is big enough as it is (and, other complicated message threads will appear below, anyway), so we'll keep it simple and stick with the assumption about deletions that was originally made.

Operations on Course Sections

The operation

is a responsibility of ``Course Section.'' It is necessary to send a message in order for this command to be executed correctly, because the new course section must be a section for an existing course, and the information about these resides within the class, ``Course.''

In order to conform to the third guideline, ``Information and the behaviour that is related to it should reside within the same class,'' we'll make ``Select an Existing Course'' a responsibility of ``Course.'' In order to have a course identified, ``Course Section'' will send a message to ``Course'' to request that this responsibility be fulfilled, and (if the operation is successful) a ``course ID'' will returned by ``Course'' to ``Course Section'' as a response. Now, once this information is available to it, ``Course Section'' can complete the operation its own (that is, by interacting with implementation classes for windows, and so on, in order to obtain any additional information that's needed from the user, without sending other messages to problem domain classes).

Thus the message thread for (successful completion of) this operation is as follows.

Message Thread for ``Create New Course Section''

``Class'' should be listed as a collaborator for the responsibility ``Create New Course Section'' (of ``Course Section''), and a responsibility ``Select Existing Course'' should be added (with no collaborators) for ``Course.''

Assuming that ``Course'' will either return a valid ``course ID'' to ``Course Section,'' or no course ID at all (perhaps, because the user cancelled the event), the only other message threads that seem possible for this operation are as follows.

Thus, we don't need to add any other collaborators for ``Create New Course Section,'' or any other responsibilities for other classes.

The operations

are both responsibilities for ``Course Section.'' (Note that ``List Sections for Course'' is being used as the name for a command that can be selected by the user, and it will require that a ``course ID'' be discovered somehow, while ``Get Sections for Course'' has already been used as the name of a slightly different service, that other classes can use and which has a ``course ID'' as an input parameter.)

Let's assume that the information to be returned as output for the command ``List Sections for Courses'' only includes data that's internal to ``Course Section.'' Then, the above two operations have exactly the same message thread(s) and collaborators as ``Create New Course Section'' did, and no additional responsibilities for other classes are required.

However, let's suppose that a ``class list'' should be included with the information returned as output for the operation,

Furthermore, let's assume that students' names should be displayed along with ID numbers in this list.

This operation should be a responsibility of ``Course Section,'' and it will be necessary to send a message to ``Course'' in order to obtain a course ID at the beginning of its processing. In order to prepare the class list, it will be necessary to send a message to ``Grade,'' to ``Get Registrations for (the) Course Section;'' and, since students' names are to be shown along with ID numbers, it will be necessary for ``Grade'' to send a sequence of messages, ``Get Student,'' to ``Student,'' as well. The message thread for a successful operation is as follows.

Message Thread for ``Display Course Section Information''

Both ``Course'' and ``Grade'' should be collaborators for the responsibility ``Display Course Section Information'' (for the class ``Course Section''). A responsibility, ``Get Registrations for Course Section,'' with collaborator ``Student,'' should be added for ``Grade.'' Finally, a responsibility ``Get Student'' (with no collaborators) should be added for ``Course.''

Once again, message threads for error conditions and cancellations are just truncations of this one, and/or show cancel as a response instead of data. Thus no additional responsibilities or coordinators are needed for them.

Finally, the operation

is also a responsibility of ``Course Section.'' Assuming that a course section can't be deleted if any students are still registered in it, a message thread for this operation would like the following.

Message Thread for ``Delete Course Section''

The course section would be deleted if and only if the sequence of ``grades'' returned by ``Grade'' is empty.

The responsibility ``Delete Course Section'' (for ``Course Section'') should have collaborators ``Course'' and ``Grade.'' A responsibility, ``Get Grades for Section,'' should be added for ``Grade'' (with no collaborators).

Finally, the only message threads for errors or cancellations are truncations of the one shown above (again, possibly with cancel returned as a response to a message instead of data), so no additional collaborators or responsibilities need to be added for them.

Operations on Students

The operations

are all responsibilities of ``Student.'' It isn't necessary to send any messages to other problem domain classes in order to provide these services, so the message threads are trivial and none of these responsibilities has any (problem domain) collaborators.

The operation

is also a responsibility of ``Student.'' Assuming that this should include a list of the student's registrations in courses and grades received for them, and assuming that this should be reasonably descriptive (in particular, something more than a ``course ID'' is to be included for each course), a message thread for successful completion of this operation might look like the following.

Message Thread for ``Display Student Information''

Now, a responsibility ``Display Student Information'' with collaborator ``Grade'' should be added for ``Student.'' A responsibility ``Get Grades for Student'' with collaborator ``Course Section'' should be added for ``Grade.'' A responsibility ``Get Course & Section'' with collaborator ``Course'' should be added for ``Course Section.'' Finally, a responsibility ``Get Course,'' with no collaborators, should be added for ``Course'' (if it doesn't already exist).

Message threads for errors and cancellations would (as usual) just be truncations for this one, sometimes with cancel used a response instead of data, so no new collaborators or responsibilities are needed for these.

The final responsibility (corresponding to a user's command) for ``Student'' is

Now, this time, we'll assume that registrations and grades for old students can (and should be) deleted at the same time as old students. Under this assumption, a message thread for successful completion of this operation would look like the following.

Message Thread for ``Delete Old Students''

Clearly ``Grade'' should be added as a collaborator for the responsibility ``Delete Old Students,'' and a responsibility ``Delete Grades for Student'' (with no collaborators) should be added for ``Grade.'' The only message thread for an error or cancellation for this operation is probably trivial (with no messages sent at all) so, again, it requires no additional responsibilities or collaborators.

Operations on Registrations and Grades

The operations

are all responsibilities of ``Grade.'' Each requires an existing course selection (of an existing course) and an existing student to be selected, and none requires additional communication after these have been obtained. Thus, successful completion of each produces the following message thread.

Message Thread for Operations on Grades

According to the above diagram, ``Course Section'' and ``Student'' should be listed as collaborators for all three of the responsibilities of ``Grade'' given above. ``Select Existing Course Section'' should be added as a responsibility of ``Course Section,'' with collaborator ``Course.'' ``Select Existing Course'' has been added as a responsibility of ``Course'' already. Finally, ``Select Existing Student'' should be added as a responsibility of ``Student,'' with no collaborators.

Message threads for cancellations or errors are truncations of this one, so no additional collaborators or responsibilities are required for them.

Since the system already lists grade information on student information reports and on class lists for course sections, it doesn't seem necessary to add any additional commands for listing of grades - so these are all the commands that will be considered.

CRC Cards

Finally, the CRC cards obtained for ``Registrar,'' ``Course,'' ``Course Section,'' ``Student,'' and ``Grade'' are as follows.

CRC Card for Registrar

CRC Card for Course

CRC Card for Course Section

CRC Card for Student

CRC Card for Grade

Class Diagram with Message Connections

The class diagram obtained by adding the message connections we've discovered is as follows.

Class Diagram with Message Connections

Including Additional Classes

If we'd added the implementation classes that problem domain classes communicate with, then ``Task Manager'' would be listed as a collaborator for every responsibility corresponding to the (beginning of the) selection of a command. Task Manager would have at least four responsibilities - ``Start Command Processing'' and ``Finish Command Processing'' (with all the problem domain classes except for ``Registrar'' as collaborators for both), and ``Enable Menus'' and ``Disable Menus'' (with all the problem domain classes, including ``Registrar,'' as collaborators for both).

Each problem domain class is likely connected, via a whole-part structure, to one or more classes that represents part of a human-computer interface, including menu classes. Assuming that it's the menu class that is ``informed of'' one of the items it displays, there would be a message connection shown from each menu to the corresponding problem domain class, and there would also be a message connection in the opposite direction in each case.

Location: [CPSC 333] [Listing by Topic] [Listing by Date] [Previous Topic] [Next Topic] CRC Modeling Example


Department of Computer Science
University of Calgary

Office: (403) 220-5073
Fax: (403) 284-4707

eberly@cpsc.ucalgary.ca