8. JavaScript: Arrays

OBJECTIVES

In this chapter you’ll learn:

• To use arrays to store lists and tables of values.

• To declare an array, initialize an array and refer to individual elements of an array.

• To pass arrays to functions.

• To sort an array.

• To declare and manipulate multidimensional arrays.

With sobs and tears he sorted out Those of the largest size . . .
Lewis Carroll

Attempt the end, and never stand to doubt; Nothing’s so hard, but search will find it out.
Robert Herrick

Now go, write it before them in a table, and note it in a book.
Isaiah 30:8

’Tis in my memory lock’d, And you yourself shall keep the key of it.
William Shakespeare

8.1 Introduction

Arrays are data structures consisting of related data items (sometimes called collections of data items). JavaScript arrays are “dynamic” entities in that they can change size after they are created. Many of the techniques demonstrated in this chapter are used frequently in Chapters 1011 as we introduce the collections that allow a script programmer to manipulate every element of an XHTML document dynamically.

8.2 Arrays

An array is a group of memory locations that all have the same name and normally are of the same type (although this attribute is not required in JavaScript). To refer to a particular location or element in the array, we specify the name of the array and the position number of the particular element in the array.

Figure 8.1 shows an array of integer values named c. This array contains 12 elements. Any one of these elements may be referred to by giving the name of the array followed by the position number of the element in square brackets ([]). The first element in every array is the zeroth element. Thus, the first element of array c is referred to as c[0], the second element of array c is referred to as c[1], the seventh element of array c is referred to as c[6] and, in general, the ith element of array c is referred to as c[i-1]. Array names follow the same conventions as other identifiers.

Fig. 8.1 | Array with 12 elements.

Image

The position number in square brackets is called a subscript (or an index). A subscript must be an integer or an integer expression. Note that a subscripted array name is a left-hand-side expression—it can be used on the left side of an assignment to place a new value into an array element. It can also be used on the right side of an assignment to assign its value to another left-hand side expression.

Let us examine array c in Fig. 8.1 more closely. The array’s name is c. The length of array c is 12 and can be found using by the following expression:

c.length

Every array in JavaScript knows its own length. The array’s 12 elements are referred to as c[0], c[1], c[2], …, c[11]. The value of c[0] is -45, the value of c[1] is 6, the value of c[2] is 0, the value of c[7] is 62 and the value of c[11] is 78.

The brackets that enclose the array subscript are a JavaScript operator. Brackets have the same level of precedence as parentheses. The chart in Fig. 8.2 shows the precedence and associativity of the operators introduced so far. They are shown from top to bottom in decreasing order of precedence, alongside their associativity and type.

Fig. 8.2 | Precedence and associativity of the operators discussed so far.

Image

8.3 Declaring and Allocating Arrays

Arrays occupy space in memory. Actually, an array in JavaScript is an Array object. You use operator new to dynamically allocate (request memory for) the number of elements required by each array. Operator new creates an object as the program executes by obtaining enough memory to store an object of the type specified to the right of new. The process of creating new objects is also known as creating an instance or instantiating an object, and operator new is known as the dynamic memory allocation operator. Arrays are objects must be created with new. To allocate 12 elements for integer array c, use the statement

var c = new Array(12 );

The preceding statement can also be performed in two steps, as follows:

var c; // declares the array
c = new Array(12 ); // allocates the array

When arrays are allocated, the elements are not initialized—they have the value undefined.

Image

Common Programming Error 8.1

Assuming that the elements of an array are initialized when the array is allocated may result in logic errors.

8.4 Examples Using Arrays

This section presents several examples of creating and manipulating arrays.

Creating and Initializing Arrays

The script in Fig. 8.3 uses operator new to allocate an Array of five elements and an empty array. The script demonstrates initializing an Array of existing elements and also shows that an Array can grow dynamically to accommodate new elements. The Array’s values are displayed in XHTML tables.

Fig. 8.3 | Initializing the elements of an array. (Part 1 of 2.)

Image

Fig. 8.3 | Initializing the elements of an array. (Part 2 of 2.)

Image

Line 17 creates Array n1 as an array of five elements. Line 18 creates Array n2 as an empty array. Lines 21–22 use a for statement to initialize the elements of n1 to their subscript numbers (0 to 4). Note the use of the expression n1.length in the condition for the for statement to determine the length of the array. In this example, the length of the array is 5, so the loop continues executing as long as the value of control variable i is less than 5. For a five-element array, the subscript values are 0 through 4, so using the less than operator, <, guarantees that the loop does not attempt to access an element beyond the end of the array. Zero-based counting is usually used to iterate through arrays.

Lines 25–26 use a for statement to add five elements to the Array n2 and initialize each element to its subscript number (0 to 4). Note that Array n2 grows dynamically to accommodate the values assigned to each element of the array.

Image

Software Engineering Observation 8.1

JavaScript automatically reallocates an Array when a value is assigned to an element that is outside the bounds of the original Array. Elements between the last element of the original Array and the new element have undefined values.

Lines 28–29 invoke function outputArray (defined in lines 33–46) to display the contents of each array in an XHTML table. Function outputArray receives two arguments—a string to be output before the XHTML table that displays the contents of the array and the array to output. Lines 41–43 use a for statement to output XHTML text that defines each row of the table.

Image

Common Programming Error 8.2

Referring to an element outside the Array bounds is normally a logic error.

If the values of an Array’s elements are known in advance, the elements can be allocated and initialized in the declaration of the array. There are two ways in which the initial values can be specified. The statement

var n = [ 10, 20, 30, 40, 50 ];

uses a comma-separated initializer list enclosed in square brackets ([ and ]) to create a five-element Array with subscripts of 0, 1, 2, 3 and 4. The array size is determined by the number of values in the initializer list. Note that the preceding declaration does not require the new operator to create the Array object—this functionality is provided by the interpreter when it encounters an array declaration that includes an initializer list. The statement

var n = new Array(10, 20, 30, 40, 50 );

also creates a five-element array with subscripts of 0, 1, 2, 3 and 4. In this case, the initial values of the array elements are specified as arguments in the parentheses following new Array. The size of the array is determined by the number of values in parentheses. It is also possible to reserve a space in an Array for a value to be specified later by using a comma as a place holder in the initializer list. For example, the statement

var n = [ 10, 20, , 40, 50 ];

creates a five-element array with no value specified for the third element (n[ 2 ]).

Initializing Arrays with Initializer Lists

The script in Fig. 8.4 creates three Array objects to demonstrate initializing arrays with initializer lists (lines 18–20) and displays each array in an XHTML table using the same function outputArray discussed in Fig. 8.3. Note that when Array integers2 is displayed in the web page, the elements with subscripts 1 and 2 (the second and third elements of the array) appear in the web page as undefined. These are the two elements for which we did not supply values in the declaration in line 20 in the script.

Fig. 8.4 | Declaring and initializing arrays. (Part 1 of 2.)

Image

Fig. 8.4 | Declaring and initializing arrays. (Part 2 of 2.)

Image

Summing the Elements of an Array with for and for…in

The script in Fig. 8.5 sums the values contained in theArray, the 10-element integer array declared, allocated and initialized in line 13. The statement in line 19 in the body of the first for statement does the totaling. Note that the values supplied as initializers for array theArray could be read into the program using an XHTML form.

Fig. 8.5 | Summing elements of an array.

Image

In this example, we introduce JavaScript’s for…in statement, which enables a script to perform a task for each element in an array (or, as we’ll see in Chapters 1011, for each element in a collection). Lines 25-26 show the syntax of a for…in statement. Inside the parentheses, we declare the element variable used to select each element in the object to the right of keyword in (theArray in this case). When using for…in, JavaScript automatically determines the number of elements in the array. As the JavaScript interpreter iterates over theArray’s elements, variable element is assigned a value that can be used as a subscript for theArray. In the case of an Array, the value assigned is a subscript in the range from 0 up to, but not including, theArray.length. Each value is added to total2 to produce the sum of the elements in the array.

Image

Error-Prevention Tip 8.1

When iterating over all the elements of an Array, use a for…in statement to ensure that you manipulate only the existing elements of the Array. Note that a for…in statement skips any undefined elements in the array.

Using the Elements of an Array as Counters

In Chapter 7, we indicated that there is a more elegant way to implement the dice-rolling program in Fig. 7.4. The program rolled a single six-sided die 6000 times and used a switch statement to total the number of times each value was rolled. An array version of this script is shown in Fig. 8.6. The switch statement in Fig. 7.4 is replaced by line 24 of this program. This line uses the random face value as the subscript for the array frequency to determine which element to increment during each iteration of the loop. Because the random number calculation in line 23 produces numbers from 1 to 6 (the values for a six-sided die), the frequency array must be large enough to allow subscript values of 1 to 6. The smallest number of elements required for an array to have these subscript values is seven elements (subscript values from 0 to 6). In this program, we ignore element 0 of array frequency and use only the elements that correspond to values on the sides of a die. Also, lines 32–34 of this program use a loop to generate the table that was written one line at a time in Fig. 7.4. Because we can loop through array frequency to help produce the output, we do not have to enumerate each XHTML table row as we did in Fig. 7.4.

Fig. 8.6 | Dice-rolling program using an array instead of a switch. (Part 1 of 2.)

Image

Fig. 8.6 | Dice-rolling program using an array instead of a switch. (Part 2 of 2.)

Image

8.5 Random Image Generator Using Arrays

In Chapter 7, we created a random image generator that required image files to be named 1.gif, 2.gif, …, 7.gif. In this example (Fig. 8.7), we create a more elegant random image generator that does not require the image filenames to be integers. This version of the random image generator uses an array pictures to store the names of the image files as strings. The script generates a random integer and uses it as a subscript into the pictures array. The script outputs an XHTML img element whose src attribute contains the image filename located in the randomly selected position in the pictures array.

Fig. 8.7 | Random image generation using arrays. (Part 1 of 2.)

Image

Fig. 8.7 | Random image generation using arrays. (Part 2 of 2.)

Image

The script declares the array pictures in lines 16–17 and initializes it with the names of seven image files. Lines 22–23 create the img tag that displays the random image on the web page. Line 22 opens the img tag and begins the src attribute. Line 23 generates a random integer from 0 to 6 as an index into the pictures array, the result of which is a randomly selected image filename. The expression

pictures[ Math.floor( Math.random() * 7 ) ]

evaluates to a string from the pictures array, which then is written to the document (line 23). Line 23 completes the img tag with the extension of the image file (.gif).

8.6 References and Reference Parameters

Two ways to pass arguments to functions (or methods) in many programming languages are pass-by-value and pass-by-reference. When an argument is passed to a function by value, a copy of the argument’s value is made and is passed to the called function. In Java-Script, numbers, boolean values and strings are passed to functions by value.

With pass-by-reference, the caller gives the called function direct access to the caller’s data and allows it to modify the data if it so chooses. This procedure is accomplished by passing to the called function the address of the location in memory where the data resides. Pass-by-reference can improve performance because it can eliminate the overhead of copying large amounts of data, but it can weaken security because the called function can access the caller’s data. In JavaScript, all objects (and thus all Arrays) are passed to functions by reference.

Image

Error-Prevention Tip 8.2

With pass-by-value, changes to the copy of the called function do not affect the original variable’s value in the calling function. This prevents the accidental side effects that so greatly hinder the development of correct and reliable software systems.

Image

Software Engineering Observation 8.2

Unlike some other languages, JavaScript does not allow you to choose whether to pass each argument by value or by reference. Numbers, boolean values and strings are passed by value. Objects are passed to functions by reference. When a function receives a reference to an object, the function can manipulate the object directly.

Image

Software Engineering Observation 8.3

When returning information from a function via a return statement, numbers and boolean values are always returned by value (i.e., a copy is returned), and objects are always returned by reference. Note that, in the pass-by-reference case, it is not necessary to return the new value, since the object is already modified.

To pass a reference to an object into a function, simply specify the reference name in the function call. Normally, the reference name is the identifier that the program uses to manipulate the object. Mentioning the reference by its parameter name in the body of the called function actually refers to the original object in memory, which can be accessed directly by the called function. In the next section, we demonstrate pass-by-value and pass-by-reference, using arrays.

8.7 Passing Arrays to Functions

To pass an array argument to a function (Fig. 8.8), specify the name of the array (a reference to the array) without brackets. For example, if array hourlyTemperatures has been declared as

Fig. 8.8 | Passing arrays and individual array elements to functions. (Part 1 of 2.)

Image

Fig. 8.8 | Passing arrays and individual array elements to functions. (Part 2 of 2.)

Image

var hourlyTemperatures = new Array(24 );

then the function call

modifyArray( hourlyTemperatures );

passes array hourlyTemperatures to function modifyArray. As stated in Section 8.2, every array object in JavaScript knows its own size (via the length attribute). Thus, when we pass an array object into a function, we do not pass the size of the array separately as an argument. Figure 8.3 illustrated this concept when we passed Arrays n1 and n2 to function outputArray to display each Array’s contents.

Although entire arrays are passed by reference, individual numeric and boolean array elements are passed by value exactly as simple numeric and boolean variables are passed (the objects referred to by individual elements of an Array of objects are still passed by reference). Such simple single pieces of data are called scalars. To pass an array element to a function, use the subscripted name of the element as an argument in the function call.

For a function to receive an Array through a function call, the function’s parameter list must specify a parameter that will refer to the Array in the body of the function. Unlike other programming languages, JavaScript does not provide a special syntax for this purpose. JavaScript simply requires that the identifier for the Array be specified in the parameter list. For example, the function header for function modifyArray might be written as

function modifyArray( b )

indicating that modifyArray expects to receive a parameter named b (the argument supplied in the calling function must be an Array). Arrays are passed by reference, and therefore when the called function uses the array name b, it refers to the actual array in the caller (array hourlyTemperatures in the preceding call). The script in Fig. 8.8 demonstrates the difference between passing an entire array and passing an array element.

Image

Software Engineering Observation 8.4

JavaScript does not check the number of arguments or types of arguments that are passed to a function. It is possible to pass any number of values to a function. JavaScript will attempt to perform conversions when the values are used.

The statement in line 17 invokes function outputArray to display the contents of array a before it is modified. Function outputArray (defined in lines 32–36) receives a string to output and the array to output. The statement in lines 34–35 uses Array method join to create a string containing all the elements in theArray. Method join takes as its argument a string containing the separator that should be used to separate the elements of the array in the string that is returned. If the argument is not specified, the empty string is used as the separator.

Line 19 invokes function modifyArray (lines 39–43) and passes it array a. The modifyArray function multiplies each element by 2. To illustrate that array a’s elements were modified, the statement in line 21 invokes function outputArray again to display the contents of array a after it is modified. As the screen capture shows, the elements of a are indeed modified by modifyArray.

To show the value of a[3] before the call to modifyElement, line 25 outputs the value of a[3]. Line 27 invokes modifyElement (lines 46–51) and passes a[3] as the argument. Remember that a[3] actually is one integer value in the array a. Also remember that numeric values and boolean values are always passed to functions by value. Therefore, a copy of a[3] is passed. Function modifyElement multiplies its argument by 2 and stores the result in its parameter e. The parameter of function modifyElement is a local variable in that function, so when the function terminates, the local variable is no longer accessible. Thus, when control is returned to the main script, the unmodified value of a[3] is displayed by the statement in line 29.

8.8 Sorting Arrays

The Array object in JavaScript has a built-in method sort for sorting arrays. Figure 8.9 demonstrates the Array object’s sort method.

Fig. 8.9 | Sorting an array with Array method sort. (Part 1 of 2.)

Image

Fig. 8.9 | Sorting an array with Array method sort. (Part 2 of 2.)

Image

By default, Array method sort (with no arguments) uses string comparisons to determine the sorting order of the Array elements. The strings are compared by the ASCII values of their characters. [Note: String comparison is discussed in more detail in Chapter 9, JavaScript: Objects.] In this example, we’d like to sort an array of integers.

Method sort takes as its optional argument the name of a function (called the comparator function) that compares its two arguments and returns one of the following:

• a negative value if the first argument is less than the second argument

• zero if the arguments are equal, or

• a positive value if the first argument is greater than the second argument

This example uses function compareIntegers (defined in lines 27–30) as the comparator function for method sort. It calculates the difference between the integer values of its two arguments (function parseInt ensures that the arguments are handled properly as integers). If the first argument is less than the second argument, the difference will be a negative value. If the arguments are equal, the difference will be zero. If the first argument is greater than the second argument, the difference will be a positive value.

Line 16 invokes Array object a’s sort method and passes the name of function compareIntegers as an argument. Method sort receives function compareIntegers as an argument, then uses the function to compare elements of the Array a to determine their sorting order.

Image

Software Engineering Observation 8.5

Functions in JavaScript are considered to be data. Therefore, functions can be assigned to variables, stored in Arrays and passed to functions just like other data types.

8.9 Multidimensional Arrays

Multidimensional arrays with two subscripts are often used to represent tables of values consisting of information arranged in rows and columns. To identify a particular table element, we must specify the two subscripts; by convention, the first identifies the element’s row, and the second identifies the element’s column. Arrays that require two subscripts to identify a particular element are called two-dimensional arrays.

Multidimensional arrays can have more than two dimensions. JavaScript does not support multidimensional arrays directly, but does allow you to specify arrays whose elements are also arrays, thus achieving the same effect. When an array contains one-dimensional arrays as its elements, we can imagine these one-dimensional arrays as rows of a table, and the positions in these arrays as columns. Figure 8.10 illustrates a two-dimensional array named a that contains three rows and four columns (i.e., a three-by-four array—three one-dimensional arrays, each with 4 elements). In general, an array with m rows and n columns is called an m-by-n array.

Fig. 8.10 | Two-dimensional array with three rows and four columns.

Image

Every element in array a is identified in Fig. 8.10 by an element name of the form a[i][j]; a is the name of the array, and i and j are the subscripts that uniquely identify the row and column, respectively, of each element in a. Note that the names of the elements in the first row all have a first subscript of 0; the names of the elements in the fourth column all have a second subscript of 3.

Arrays of One-Dimensional Arrays

Multidimensional arrays can be initialized in declarations like a one-dimensional array. Array b with two rows and two columns could be declared and initialized with the statement

var b = [ [ 1, 2 ], [ 3, 4 ] ];

The values are grouped by row in square brackets. The array [1, 2] initializes element b[0], and the array [3, 4] initializes element b[1]. So 1 and 2 initialize b[0][0] and b[0][1], respectively. Similarly, 3 and 4 initialize b[1][0] and b[1][1], respectively. The interpreter determines the number of rows by counting the number of sub initializer lists—arrays nested within the outermost array. The interpreter determines the number of columns in each row by counting the number of values in the sub-array that initializes the row.

Two-Dimensional Arrays with Rows of Different Lengths

The rows of a two-dimensional array can vary in length. The declaration

var b = [ [ 1, 2 ], [ 3, 4, 5 ] ];

creates array b with row 0 containing two elements (1 and 2) and row 1 containing three elements (3, 4 and 5).

Creating Two-Dimensional Arrays with new

A multidimensional array in which each row has a different number of columns can be allocated dynamically, as follows:

var b;
b = new Array(2 ); // allocate rows
b[ 0 ] = new Array(5); // allocate columns for row 0
b[ 1 ] = new Array(3); // allocate columns for row 1

The preceding code creates a two-dimensional array with two rows. Row 0 has five columns, and row 1 has three columns.

Two-Dimensional Array Example: Displaying Element Values

Figure 8.11 initializes two-dimensional arrays in declarations and uses nested for…in loops to traverse the arrays (i.e., manipulate every element of the array).

Fig. 8.11 | Initializing multidimensional arrays. (Part 1 of 2.)

Image

Fig. 8.11 | Initializing multidimensional arrays. (Part 2 of 2.)

Image

The program declares two arrays in main script (in the XHTML head element). The declaration of array1 (lines 12–13 provides six initializers in two sublists. The first sublist initializes the first row of the array to the values 1, 2 and 3; the second sublist initializes the second row of the array to the values 4, 5 and 6. The declaration of array2 (lines 14–16) provides six initializers in three sublists. The sublist for the first row explicitly initializes the first row to have two elements, with values 1 and 2, respectively. The sublist for the second row initializes the second row to have one element, with value 3. The sublist for the third row initializes the third row to the values 4, 5 and 6.

The script calls function outputArray from lines 18–19 to display each array’s elements in the web page. Function outputArray (lines 21–37) receives two arguments—a string heading to output before the array and the array to output (called theArray). Note the use of a nested for…in statement to output the rows of each two-dimensional array. The outer for…in statement iterates over the rows of the array. The inner for…in statement iterates over the columns of the current row being processed. The nested for…in statement in this example could have been written with for statements, as follows:

for ( var i = 0; i < theArray.length; ++i )
{
   for ( var j = 0; j < theArray[ i ].length; ++j )  
      document.write( theArray[ i ][ j ] + " " );

   document.writeln( "<br/>" );
}

In the outer for statement, the expression theArray.length determines the number of rows in the array. In the inner for statement, the expression theArray[i].length determines the number of columns in each row of the array. This condition enables the loop to determine, for each row, the exact number of columns.

Common Multidimensional-Array Manipulations with for and for…in Statements

Many common array manipulations use for or for…in statements. For example, the following for statement sets all the elements in the third row of array a in Fig. 8.10 to zero:

for (var col = 0; col < a[ 2 ].length; ++col )
    a[ 2 ][ col ] = 0;

We specified the third row; therefore, we know that the first subscript is always 2 (0 is the first row and 1 is the second row). The for loop varies only the second subscript (i.e., the column subscript). The preceding for statement is equivalent to the statements

a[ 2 ][ 0 ] = 0;
a[ 2 ][ 1 ] = 0;
a[ 2 ][ 2 ] = 0;
a[ 2 ][ 3 ] = 0;

The following for…in statement is also equivalent to the preceding for statement:

for (var col in a[ 2 ] )
    a[ 2 ][ col ] = 0;

The following nested for statement determines the total of all the elements in array a:

var total = 0;

for ( var row = 0; row < a.length; ++row )

    for ( var col = 0; col < a[ row ].length; ++col )
      total += a[ row ][ col ];

The for statement totals the elements of the array, one row at a time. The outer for statement begins by setting the row subscript to 0, so that the elements of the first row may be totaled by the inner for statement. The outer for statement then increments row to 1, so that the elements of the second row can be totaled. Then the outer for statement increments row to 2, so that the elements of the third row can be totaled. The result can be displayed when the nested for statement terminates. The preceding for statement is equivalent to the following for…in statement:

var total = 0;

for ( var row in a )

   for ( var col in a[ row ] )
      total += a[ row ][ col ];

8.10 Building an Online Quiz

Online quizzes and polls are popular web applications often used for educational purposes or just for fun. Web developers typically build quizzes using simple XHTML forms and process the results with JavaScript. Arrays allow a programmer to represent several possible answer choices in a single data structure. Figure 8.12 contains an online quiz consisting of one question. The quiz page contains one of the tip icons used throughout this book and an XHTML form in which the user identifies the type of tip the image represents by selecting one of four radio buttons. After the user selects one of the radio button choices and submits the form, the script determines whether the user selected the correct type of tip to match the mystery image. The JavaScript function that checks the user’s answer combines several of the concepts from the current chapter and previous chapters in a concise and useful script.

Fig. 8.12 | Online quiz graded with JavaScript. (Part 1 of 2.)

Image

Fig. 8.12 | Online quiz graded with JavaScript. (Part 2 of 2.)

Image

Before we discuss the script code, we first discuss the body element (lines 25–48) of the XHTML document. The body’s GUI components play an important role in the script.

Lines 26–47 define the form that presents the quiz to users. Line 26 begins the form element and specifies the onsubmit attribute to "checkAnswers()", indicating that the interpreter should execute the JavaScript function checkAnswers (lines 12–21) when the user submits the form (i.e., clicks the Submit button or presses Enter).

Line 29 adds the tip image to the page. Lines 32–42 display the radio buttons and corresponding labels that display possible answer choices. Lines 44–45 add the submit and reset buttons to the page.

We now examine the script used to check the answer submitted by the user. Lines 12– 21 declare the function checkAnswers that contains all the JavaScript required to grade the quiz. The if...else statement in lines 17–20 determines whether the user answered the question correctly. The image that the user is asked to identify is the Error-Prevention Tip icon. Thus the correct answer to the quiz corresponds to the second radio button.

An XHTML form’s elements can be accessed individually using getElementById or through the elements property of the containing form object. The elements property contains an array of all the form’s controls. The radio buttons are part of the XHTML form myQuiz, so we access the elements array in line 17 using dot notation (myQuiz.elements[ 1 ]). The array element myQuiz.elements[ 1 ] corresponds to the correct answer (i.e., the second radio button). Finally, line 17 determines whether the property checked of the second radio button is true. Property checked of a radio button is true when the radio button is selected, and it is false when the radio button is not selected. Recall that only one radio button may be selected at any given time. If property myQuiz.elements[ 1 ].checked is true, indicating that the correct answer is selected, the script alerts a congratulatory message. If property checked of the radio button is false, then the script alerts an alternate message (line 20).

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset