The modulus operator, represented by the percent symbol ((`%`), is the last unmentioned binary operator of Table 7.1. The modulus operator has the same precedence as the division and multiplication operators. It can only be used with integer numbers and returns the remainder of dividing the first (left) operand with the second (right) operand. For example `20 % 7` is 6 because 7 goes into 20 two times, 2 * 7 = 14 and 20 - 14 = 6, which is the remainder. An often-used algebraic notation to denote a modulus calculation is the abbreviation mod. Thus, 20 % 7 in mathematics is often written 20 mod 7. Table 7.2 gives an overview of the five binary operators and how typical arithmetic expression are written in C#.

Operation | Symbol | Arithmetic Expression | C# Expression |
---|---|---|---|

Addition | + | cost + 100 | cost + 100 |

Subtraction | - | 20 sum | 20 - sum |

Multiplication | * | pricextax or price tax | price * tax |

Division | / | p/q or p÷q or P | p/q |

Modulus | % | x mod y | x % y |

The modulus operator is useful for solving many more programmatic problems than its simple appearance seems to indicate. For example, consider a program containing an algorithm that, among other things, is counting numbers (1, 2, 3, 4, 5, 6, 7, and so on) with a variable called `count`. You want to detect every number counted that is divisible by two. To solve this programmatic problem, you merely need to ask if `(count % 2)` is equal to zero, because the numbers 2, 4, 6, and so on have a remainder of 0 when divided by two. This method also applies when finding numbers divisible by 3, 4, 5, and so on.

Another useful application is conversions from one unit to another, such as converting inches to feet and inches or dollars to quarters, dimes, nickels, and pennies.

The following case study shows the modulus operator in action. It is used to find every 7^{th} number in a list of numbers { 1, 2, 3, 4, 5, 6, 7, and so on} representing days in a day-counting algorithm.

Software Specification

The algorithm described here could be part of the internal timekeeper system of an elevator simulation program. It simulates "days" passing by and, consequently, determines which day it is inside the simulation and perhaps whether it is a busy day or a holiday. It also enables the user of the simulation program to determine the total amount of "days" the "elevator system" will run during one particular simulation.

Our algorithm must count the "days" for which the simulated elevator system has been running. Additionally, it is required to report how many "weeks" and "days" for which the simulation has lasted. For example, if the system has run for 23 days, we want the algorithm to report 3 weeks and 2 days.

Finally, the algorithm must provide a signal to the elevator control system whenever the current "day" is a "Sunday." The latter is important because the system goes into a "low-traffic" mode on "Sundays" for efficiency purposes.

Software Design:

We will jump straight to the algorithm design stage of the software design process, because the specification only involves a very small isolated piece of software (the algorithm), rendering the class and method identification stages superfluous.

Algorithm Design of Internal Method:

Which variables should the algorithms contain? The algorithm will certainly have to know the total running time (in days) of the elevator system. We can call this variable `maxSimulationDays` and, because it is holding a whole positive number of days, we choose it to be of the unsigned integer type `uint`. The simulation will further have to keep track of the current number of days the elevator system has been running. This will be represented by the `dayCounter` variable, also of type `uint`.

We then need a loop. Every time the loop is repeated, the `dayCounter` will be incremented by one, the weeks and days will be reported, a Sunday check will be made and an alert reported if it turns out to be Sunday.

The loop will stop when the value of `dayCounter` has reached the value of `maxSimulationDays`.

How do we then convert the amount held by `dayCounter` into weeks and days? The number of weeks is a straightforward division, `(dayCounter / 7)` which, because we are dealing with integers, will return the whole number of times 7 goes into `dayCounter`. We then need to find the few remaining days, yes, this is where the modulus operator comes into the picture. The calculation `(dayCounter % 7)` will do the trick. We now just need a way to detect every Sunday. A Sunday is simply set to be every 7^{th} day counted. But how can the algorithm detect every 7^{th} day passing by? Clearly, the days 7, 14, 21, 28, … are all divisible by 7. Consequently, if `(dayCounter % 7)` is equal to 0, it's Sunday.

Let's look at the resulting algorithm presented with pseudocode in Listing 7.1. It keeps track of the current day, reports of running time in weeks and days, and alerts when the current day is a Sunday.

01: Set the variable dayCounter to 0 02: Set the maxSimulationDays to total days the elevator system should run for 03: While dayCounter is less than maxSimulationDays repeat the following block 04: { 05: Increase dayCounter by one 06: Calculate and report number of weeks in dayCounter report remaining number of days. 07: If dayCounter is divisible by 7 send message ("It's Sunday") to the elevator controller and print: "Hey Hey It's Sunday!" 08: If used as part of larger simulation program then start elevator simulation lasting one day 09: } 10: Let user know that the simulation has ended

The algorithm contains a loop (lines 3 9) that repeats lines 5 8 as long as `dayCounter` is less than the `maxSimulationDays`.

It's time to construct the C# code based on the pseudocode. I decided to put the algorithm into the `Main()` method of the program because we are merely testing a freestanding prototype algorithm. Here is an overview of how the lines of the pseudocode correspond to the lines of the C# source code in Listing 7.2, the final source code.

Pseudocode line | Equivalent C# source code line |
---|---|

01 | 16 |

02 | 21 23 |

03 | 24 |

04 | 25 |

05 | 26 |

06 | 27 30 |

07 | 31 33 |

08 | 34 |

09 | 37 |

10 | 38 |

01: using System; 02: 03: /* 04: * The DayCounter class contains a prototype for 05: * a "Day counter" algorithm with potential use 06: * in an elevator simulation. 07: * It keeps track of the current day in simulation 08: * It reports of running time in days and weeks 09: * and alerts when current day is a Sunday 10: */ 11: 12: class DayCounter 13: { 14: public static void Main() 15: { 16: uint dayCounter = 0; 17: uint maxSimulationDays; 18: uint weeks; 19: byte remainderDays; 20: 21: Console.Write("Please enter the number of days " + 22: "the simulation should run for "); 23: maxSimulationDays = Convert.ToUInt32(Console.ReadLine()); 24: while(dayCounter < maxSimulationDays) 25: { 26: dayCounter++; 27: weeks = dayCounter / 7; 28: remainderDays = (byte)(dayCounter % 7); 29: Console.WriteLine("Weeks: " + weeks + 30: " Days: " + remainderDays); 31: if(remainderDays == 0) 32: // TODO send "it's Sunday" message to controller 33: Console.WriteLine("\t\tHey Hey It's Sunday!"); 34: // TODO start simulation lasting for one day. 35: // Let the program pause for 200 milliseconds 36: System.Threading.Thread.Sleep(200); 37: } 38: Console.WriteLine("Simulation ended"); 39: } 40: }

In the following output, the user specifies the simulated elevator system to run for 15 days.

` Please enter the number of days the simulation should run for 15<enter> Weeks: 0 Days: 1 Weeks: 0 Days: 2 Weeks: 0 Days: 3 Weeks: 0 Days: 4 Weeks: 0 Days: 5 Weeks: 0 Days: 6 Weeks: 1 Days: 0 Hey Hey It's Sunday! Weeks: 1 Days: 1 Weeks: 1 Days: 2 Weeks: 1 Days: 3 Weeks: 1 Days: 4 Weeks: 1 Days: 5 Weeks: 1 Days: 6 Weeks: 2 Days: 0 Hey Hey It's Sunday! Weeks: 2 Days: 1 Simulation ended `

Lines 24 37 contain a `while` loop. The braces in lines 25 and 37 surround the block of the `while` loop, which is repeatedly executed as long as the condition `(dayCounter < maxSimulationDays)` (meaning `dayCounter` less than `maxSimulationDays`) is `true`. When this condition is evaluated to be `false` in line 24, the program will continue with line 38.

Line 26 increases the value of `dayCounter` by one.

Line 27 calculates the number of whole weeks in `dayCounter`. Because all variables involved in this calculation are of type `uint`, a whole number will be assigned to `weeks`.

Line 28 calculates the remaining days of a week using the modulus operator (%). `RemainderDays` is of type `byte` and the `(dayCounter % 7)` expression is of type `uint`, so an explicit cast is required using the `(byte)` cast operator.

Because `remainderDays` is equal to `(dayCounter % 7)` due to line 28, we need to ask whether `remainderDays` is equal to zero to find out whether today is Sunday. This is done with an `if` statement in line 31.

Programmers often use `TODO` as a reminder for them of things that still remain to be done in a program. `TODO` marked comments in the program can easily be tracked down by the `find` command of the source code editor. Line 32 is simply stating that in case this program was part of a real simulation source program, this is where the `It's Sunday` message would be sent to the elevator controller system of the program.

Note that you could use any arbitrary sequence of letters instead of `TODO`, such as `REMINDME`. However, `TODO` is now so ingrained in the programming community that a sophisticated IDE, such as Visual Studio .NET, recognizes `TODO` comments and also automatically inserts them at relevant places.

Line 33 uses the TAB (`\t`) escape character twice to indent the text "Hey Hey It's Sunday!" which is printed out accordingly.

For now, just think of line 36 as a peculiar way of saying pause the program here for 200 milliseconds. The pause will cause the program to write its output in a slower and, in my opinion, more pleasant manner. Feel free to adjust the number 200 if you want to speed up (by decreasing the number) or slow down the program (by increasing the number).

Note

The previous implementation (like most algorithms) could have been designed in several different ways that rely less on the modulus operator. However, the algorithm presented certainly constitutes a valid efficient algorithm. |

C Primer Plus (5th Edition)

ISBN: 0672326965

EAN: 2147483647

EAN: 2147483647

Year: 2000

Pages: 286

Pages: 286

Authors: Stephen Prata

Similar book on Amazon

flylib.com © 2008-2017.

If you may any questions please contact us: flylib@qtcs.net

If you may any questions please contact us: flylib@qtcs.net