CPSC 217: Assignment 4

Due at 4 PM. For assignment due dates see the main schedule on the course webpage. The program must be written and run under python version 3.X.

New Concepts to be applied for the assignment

Only new concepts that need to be applied in the assignment are listed, concepts previously applied in other assignments may be needed in the implementation of your solution.

Critical design requirements

All instructions must be enclosed within the body of a function, you must write at least 5 functions (JT's solution to A4 had 9 functions written) of your own. Functions that I have created in the starting code isn't included in the count. The functions you write must be properly implemented. No global variables  may be employed. 

The exceptions to including all code inside the body of a function could include: import statements (not really needed for this assignment), the creation of global constants (e.g. ATTIC = 1), a global debugging flag and the call to the initial start or main function.

Contrary to student rumors these penalties are not specified in order to "curve the grades down" or to only allow a certain number of students to pass the course. Besides learning the mechanics of defining and calling functions you need to use them properly. For instances you shouldn't complete a course that teaches you how to write short stories and pen tales that are grammatically correct and may even use metaphorical references and include multiple characters if they include hackneyed metaphors and shallow character development. Because the penalties are quite strict then typically most/all (hopefully the latter) students will implement their solutions in the correct fashion.

Resources:

Summary:

You are to implement a text-based biological simulation: Conway's "Game of Life". Given a starting pattern of life forms in the simulation ('biosphere') the program will update the pattern according to new births and deaths that occur during that time period (turn).  Each location (element in a 2D list) in a biosphere either contains: an empty space or a life form ("Critter"). As each turn passes in the simulation a new life form may be born into an empty square or an existing Critter may die off in an occupied location. To get any credit for your submission your program must be able to initialize the two lists using any of the 6 starting patterns and it must display the before/after state of the world with the same appearance as the code provided in the display function.

Initialization of the program

Important grading point: One requirement in order to get any credit for this assignment your program must, at a minimum, use the six starting patterns: oneEmpty()twoSingleCritter(), threeSingleBirth()fourthSimpleBirth(),fifthCreateListEdgeCases() and sixthComplexCases()The more of the initial six cases that your program can correctly process, the higher will be your grade. Each of the functions will initialize a 10x10 list. Your program does not have to handle lists of other sizes. When it first runs your program must allow the user to choose via a menu which of the 6 starting patterns will be used for the simulation. You can write additional functions with different initial patterns but your program must handle the 6 starting cases. Although additional test cases won't increase your grade it may reduce the likelihood of bugs in your program (increased testing should decrease the probability of a bug). The choice of starting pattern will only appear once at the beginning. After the choice has been made the program will apply the rules of births and deaths.

Important grading point: Your program functionality marks will only be awarded if your program produces the same results as these outputs. For example, function "oneEmpty()" starts out empty and shouldnever contain a Critter in the pattern. Function "sixthComplexCases()" will produce a stable pattern of 4 Critters in a square by turn 20. Partial marks will not be awarded if your pattern of Critters is 'close' to the pattern produced my program. In addition you need to correctly and comprehensively document which starting patterns that your program will handle. Both of these requirements (producing the same patterns in your output and documenting which cases that your program correctly handles are necessary to make the marking process reasonable - don't expect the marker to expend time hand tracing code to figure out if things are working). However, providing the results that your program must display is also an advantage for you. You will know if your program is "working or not" based on the pattern match (immediate and continuous feedback about your progress). But looking at the patterns is not a substitute for implementing and employing a debugging mode. The debugging mode can be very useful for helping you determine why and how your program is malfunctioning (if you have good debugging output messages)

The code in the starting program is extremely simple and just initializes the references to the lists ('newWorld' and 'oldWorld') to an empty world and displays the result for these lists. The program that you submit will not do things this way.  The old world  is the state of the biosphere before the birth/death rules have been applied during that turn while the new world is the state after those rules were applied. The starting code does apply those rules, you need to write the code yourself to get credit.

Displaying the state of the world (before and after) during the simulation

Important grading point: As mentioned another requirement to get any credit for your assignment is that the display of the grid must be done using the display() function Even the grid is required because it makes the display of world easier to read and interpret for both you and the marker.

Running the simulation

After initializing the starting positions, the program will simulate the births and deaths of the critters over time on a turn-by-turn basis. The user can either hit <enter> to advance the simulation by another turn, 'q' or 'Q' to end the simulation.  A hidden feature (not displayed as a menu option), the [debug mode] can be toggled by entering 'd' or 'D' when prompted to proceed to another turn.

Rules of births and deaths

The births and deaths of critters is based solely upon the number of neighbors in adjacent/neighboring squares. Each square will have from 3 - 8 neighboring squares (inner squares have 8, outer squares can have 3 at the corners or 5 on the top/bottom/left/right edges). The square where the possibility of a birth or death is being examined is marked with a question mark ? in the examples below.

   
  ?
 
     
  ?  
     
 
   
     
 
Bottom right corner   An inner square   Top row  

Births (square is currently empty)

A birth can occur in an empty square if that square has exactly 3 neighbors, some (non-exhaustive) examples:

 *    
 * ?  
    * 
 
 *    
  ?  
 *   * 

Deaths (square currently contains a Critter).

A Critter can die of loneliness if it has no neighbors or only one neighbor.

     
  ?  
     
 
     
  ?  
   *  

A Critter can die of overcrowding if it has four or more neighbors (non-exhaustive number of examples below):

 *    
 * ?  *
  *   
 
 * ?
 * *

The Critter will continue living if it has 2 or 3 neighbors.

? *
 * *

Births and deaths will occur simultaneously in the simulation. How do the rules of births and deaths relate to the 10x10 world? Each turn the check for births and deaths must be made in each of the 100 squares with the rules apparently being applied at the same time. Hint for how things appear simultaneous: As mentioned the 'old' world contains the state of the biosphere for that turn before the rules have been applied and the 'new' world will track the after state.

Links to online web-based executable versions of the Game of Life:

Debugging mode

Entering 'd' or 'D' will toggle debugging mode (False becomes True, True becomes False). The flag 'debugOn' will track whether debugging message are to appear or not and by default the mode is 'off'.

    debugOn = False

When the flag is set to 'True' debugging messages will appear, otherwise they will not:

    if(debugOn == True):
        print("<<<Some debugging message>>>")

The exact content of the debugging messages is left to your discretion. As the name implies the debugging tool should be used to help you test and debug your program. Here are examples of debugging messages: 1) Display greater details: the neighbor count as well as births and deaths for each square  2) More sparse annoucements specifying only where births and deaths have occurred. Again you are not bound to produce these exact messages in order to get credit for the debugging feature but they are provided to give you an idea of how you can use this feature to test your program.

This global variable for the debugging flag is the sole exception on the prohibition on the use of global variables in your program. No penalty will be applied for using this debugging flag but the usual penalty will be applied for other global variables e.g

turn= 1

def display(oldWorld,newWorld):

    print("Turn #%d" %turn)

Global constants (e.g. SIZE = 10) should be used when appropriate. Penalties for lack of constants may be applied when it's appropriate to define one and one hasn't been defined for that program.

In addition to grading on whether the above functionality was correctly implemented TAs will also look at documentation and style.

Non-functional assignment requirements (style and documentation).

Reminder of critical style requirements

Don't forget that [critical design requirements] (proper use of functions, no global variables) must also be followed.

 

Marking and grading

Method of submission:

You are to submit your assignment using D2L [help link]. Make sure that you [check the contents of your submitted files] (e.g., is the file okay or was it corrupted, is it the correct version etc.). It's your responsibility to do this! (Make sure that you submit your assignment with enough time before it comes due for you to do a check). If don't check and there were problems with the submission then you should not expect that you can "learn your lesson" and simply resubmit.

D2L configuration for this course

Late submissions for full assignments when there is no extension granted: Make sure you give yourself enough time to complete the submission process so you don't get cut off by D2L's deadline (or your submission will be automatically flagged as late by D2L and it will be graded appropriately)..

Submission received:

On time

Hours late : >0 and <=24

Hours late: >24 and <=48

Hours late: >48 and <=72

Hours late: >72 and <=96

Hours late: >96

Penalty:

None

-1 GPA

-2 GPA

-3 GPA

-4 GPA

No credit (not accepted)

Collaboration:

Assignments must reflect individual work; group work is not allowed in this class nor can you copy the work of others. Some "do nots" for your solution: don't publically post it, don't email it out, don't show it to other students.  For more detailed information as to what constitutes academic misconduct (i.e., cheating) for this course please read the following [link].

Use of pre-created Python libraries:

Unless otherwise told you are to write the code yourself and not use any pre-created functions (or methods). For most assignments the usual acceptable functions include: print()input() and the 'conversion' functions such as int()float()str(). Look at the particular assignment description for a list of other functions/methods that you are allowed to use and still get credit in an assignment submission. If it's not listed then you should assume that you won't be able use the function and still be awarded credit. Note: This is a prohibition on using functions that someone else has wrote. You can (actually must) define your own functions for this assignment.