7.2. Using ArraysThis section considers three aspects of the use of arrays: processing ordered arrays, reading part of an array, and passing arrays to procedures. Ordered ArraysAn array is said to be ordered if its values are in either ascending or descending order. The following arrays illustrate the different types of ordered and unordered arrays. In an ascending ordered array, the value of each element is less than or equal to the value of the next element. That is,
For string arrays, the ANSI table is used to evaluate the "less than or equal to" condition. Ordered Ascending Numeric Array
Ordered Descending Numeric Array
Ordered Ascending String Array
Ordered Descending String Array
Unordered Numeric Array
Unordered String Array
Ordered arrays can be searched more efficiently than unordered arrays. In this section, we use their order to shorten the search. The technique used here is applied to searching text files in Chapter 8. Example 1. |
The following program places an ordered list of names into an array, requests a name as input, and informs the user if the name is in the list. Because the list is ordered, the search of the array ends when an element is reached whose value is greater than or equal to the input name. On average, only half the ordered array will be searched. Figure 7.3 shows the flowchart for this search. Figure 7.3. Flowchart for a search of an ordered array.
'Create array to hold 10 strings Dim nom() As String = {"AL", "BOB", "CARL", "DON", "ERIC", _ "FRED", "GREG", "HERB", "IRA", "JACK"} Private Sub btnSearch_Click(...) Handles btnSearch.Click 'Search for a name in an ordered list Dim name2Find As String Dim n As Integer = -1 name2Find = txtName.Text.ToUpper Do n += 1 'Add 1 to n Loop Until (nom(n) >= name2Find) Or (n = 9) 'Interpret result of search If nom(n) = name2Find Then txtResult.Text = "Found." [Run, type "Don" into the text box, and click the button.]
|
In some programs, we must dimension an array before knowing how many pieces of data are to be placed into it. In these cases, we dimension the array large enough to handle all reasonable contingencies. For instance, if the array is to hold exam grades, and class sizes are at most 100 students, we use a statement such as Dim grades(99) As Integer. In such situations, we must employ a counter variable to keep track of the number of values actually stored in the array. We create this counter variable using a Dim statement in the Declarations section of the program so that all procedures will have access to it.
The following program requests a list of companies and then displays them along with a count: 'Demonstrate using part of an array Dim stock(99) As String Dim counter As Integer Private Sub btnRecord_Click(...) Handles btnRecord.Click If (counter < 99) Then counter += 1 'Increment counter by 1 stock(counter - 1) = txtCompany.Text txtCompany.Clear() txtCompany.Focus() txtNumber.Text = CStr(counter) Else MsgBox("No space to record additional companies.", 0, "") txtCompany.Clear() btnSummarize.Focus() End If End Sub [Run, type in the seven companies shown (press Record Name after each company name is typed), and press Summarize.]
|
Suppose that you have two ordered lists of customers (possibly with some customers on both lists) and you want to consolidate them into a single ordered list. The technique for creating the third list, called the merge algorithm, is as follows:
Compare the two names at the top of the first and second lists.
If one name alphabetically precedes the other, copy it onto the third list and cross it off its original list.
If the names are the same, copy the name onto the third list and cross out the name from the first and second lists.
Repeat Step 1 with the current top names until you reach the end of either list.
Copy the names from the remaining list onto the third list.
The following program stores two lists of names in arrays and merges them into a third list. At most 10 names will be placed into the third array; duplicates will reduce this number. Because the variable r identifies the next position to insert a name in the third array, r 1 is the number of names in the array. Private Sub btnMerge_Click(...) Handles btnMerge.Click 'Create arrays to hold list of names Dim list1() As String = {"Al", "Carl", "Don", "Greg", "Jack"} Dim list2() As String = {"Bob", "Carl", "Eric", "Greg", "Herb"} [Run, and click the button.]
|
An array that is not declared in the Declarations section, but rather is declared in a procedure, is local to that procedure and unknown in all other procedures. However, an entire local array can be passed to another procedure. The argument in the calling statement consists of the name of the array, written without a trailing empty set of parentheses. The corresponding parameter in the header for the procedure must consist of an array name with a trailing empty set of parentheses. Like all other parameters, the array parameter must be preceded with ByVal or ByRef and followed with an "As varType" clause. The method GetUpperBound simplifies working with arrays that have been passed to a procedure.
The following program illustrates passing an array to a Function procedure. Notice that the function call is written Sum(score), not Sum(score()), and that the parameter declaration is written ByVal s() As Integer, not ByVal s As Integer. Private Sub btnCompute_Click(...) Handles btnCompute.Click 'Pass array to Function procedure Dim score() As Integer = {85, 92, 75, 68, 84, 86, 94, 74, 79, 88} txtAverage.Text = CStr(Sum(score) / 10) End Sub Function Sum(ByVal s() As Integer) As Integer 'Add up scores Dim total As Integer total = 0 For index As Integer = 0 To s.GetUpperBound(0) 'The upper bound is 9 total += s(index) 'Add the value of s(index) to the value of total Next Return total End Function [Run, and click the button.]
|
Sometimes it is also necessary to pass a class-level array from one procedure to another. For example, you might have a sorting procedure (discussed in Section 7.3) and three class-level arrays to be sorted. The sorting procedure would be called three times, each time passing a different class-level array. The method for passing a class-level array to another procedure is the same as the method for passing a local array.
The following program incorporates all three topics discussed in this section. It places ordered lists of computer languages and spoken languages into class-level arrays, requests a new language as input, and inserts the language into its proper array position (avoiding duplication). The language arrays are declared to hold up to 21 names; the variables numCompLangs and numSpokLangs record the actual number of languages in each of the ordered arrays.
Dim compLang() As String = {"ADA", "C++", "Cobol", _ "Fortran", "Java", "Visual Basic"} Dim spokLang() As String = {"Cantonese", "English", "French", _ "Mandarin", "Russian", "Spanish"} Dim numCompLangs As Integer = 6, numSpokLangs As Integer = 6 Private Sub frmAdding_Load(...) Handles MyBase.Load ReDim Preserve compLang(20) ReDim Preserve spokLang(20) End Sub [Run, type "German," and click "Add to Spoken List."]
[Type "Fortran," and click "Add to Computer List."]
|
In Examples 1 and 5, we searched successive elements of an ordered list beginning with the first element. This is called a sequential search. An efficient alternative to the sequential search is the binary search, which is considered in Section 7.4.
A single element of an array can be passed to a procedure just like any ordinary numeric or string variable.
Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim num(20) As Integer num(5) = 10 lstOutput.Items.Add(Triple(num(5))) End Sub Function Triple(ByVal x As Integer) As Integer Return 3 * x End Function
When the program is run and the button clicked, 30 will be displayed.
1. | Can an array be in both ascending and descending order at the same time? |
2. | How can the Select Case block in Example 3 be changed so all entries of both arrays (including duplicates) are merged into the third array? |
In Exercises 1 and 2, decide whether the array is ordered.
1. |
|
2. |
|
In Exercises 3 through 8, determine the output displayed when the button is clicked.
3. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim lake(4) As String lake(2) = "Michigan" DisplayThird(lake) End Sub Sub DisplayThird(ByVal lake() As String) 'Display the third element of an array txtOutput.Text = lake(2) End Sub |
4. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim num As Integer Dim square(20) As Double num = CInt(InputBox("Enter a number from 1 to 20:")) For i As Integer = 0 To num square(i) = i ^ 2 Next Total(square, num) End Sub Sub Total(ByVal list() As Double, ByVal n As Integer) Dim sum As Double = 0 For i As Integer = 0 To n sum += list(i) Next txtOutput.Text = "The sum of the " & n + 1& " numbers is "& sum End Sub (Assume that the response is 4.) |
5. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim value(4) As Integer FillArray(value) For i As Integer = 0 To 3 Select Case value(i) Case Is < value(i + 1) lstOutput.Items.Add("less than") Case Is > value(i + 1) lstOutput.Items.Add("greater than") Case Else lstOutput.Items.Add("equals") End Select Next End Sub Private Sub FillArray(ByRef list() As Integer) 'Place values into an array of five elements Dim sr As IO.StreamReader = IO.File.OpenText("DATA.TXT") For i As Integer = 0 To 4 list(i) = CInt(sr.ReadLine) Next sr.Close() End Sub (Assume that the five lines of the file DATA.TXT contain the following entries: 3, 7, 1, 1, 17.) |
6. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim ocean(5) As String ocean(1) = "Pacific" Musical(ocean(1)) End Sub Sub Musical(ByVal sea As String) txtOutput.Text = "South " & sea End Sub |
7. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim rain(11) As Double rain(0) = 2.4 rain(1) = 3.6 rain(2) = 4.0 txtOutput.Text = "total rainfall for first quarter: " & _ Total(rain, 2) & " inches" End Sub Function Total(ByVal rain() As Double, n As Integer) As Double Dim sum As Double = 0 |
8. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim num(7) As Integer Dim sr As IO.StreamReader = IO.File.OpenText("DATA.TXT") For i As Integer = 0 To 7 num(i) = CInt(sr.ReadLine) Next sr.Close() txtOutput.Text = "The array has " & Nonzero(num) & _ " nonzero entries." End Sub Function Nonzero(ByVal digit() As Integer) As Integer Dim count As Integer count = 0 For i As Integer = 0 To 7 If digit(i) <> 0 Then count += 1 End If Next Return count End Function (Assume that the eight lines of the file DATA.TXT contain the following data: 5, 0, 2, 1, 0, 0, 7, 7.) |
In Exercises 9 through 14, identify the error.
9. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim city(3) As String Assign(city) txtOutput.Text = city End Sub Sub Assign(ByRef town() As String) town(1) = "Chicago" End Sub |
10. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim planet(8) As String Assign(planet) txtOutput.Text = planet(1) End Sub Sub Assign(ByRef planet As String) planet(1) = "Venus" End Sub |
11. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click 'Multiply several positive numbers together Dim prompt As String Dim number, product, num(4) As Double Dim n As Integer = -1 prompt = "Enter a positive number to multiply by, or, " prompt &= "to see the product, Enter a negative number. " prompt &= "(Five numbers maximum can be specified.)" Do n += 1 number = CDbl(InputBox(prompt)) If number > 0 Then num(n) = number End If Loop Until (number < 0) Or (n = 4) product = 1 For i As Integer = 0 To n product = product * num(i) Next txtOutput.Text = "The product of the numbers entered is "_ & product & "." End Sub |
12. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim hue(15) As String hue(1) = "Blue" Favorite(hue()) End Sub Sub Favorite(ByVal tone() As String) tone(1) = hue(1) txtOutput.Text = tone End Sub |
13. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim a(10), b(10) As Double For i As Integer = 0 To 10 a(i) = i ^ 2 Next CopyArray(a, b) txtOutput.Text = CStr(b(10)) End Sub Sub CopyArray(ByRef a() As Double, ByRef b() As Double) 'Place a's values in b b() = a() End Sub |
14. | Private Sub btnDisplay_Click(...) Handles btnDisplay.Click Dim a(2) As Integer a(0) = 42 a(1) = 7 a(2) = 11 FlipFirstTwo(a) txtOutput.Text = a(0) & " " & a(1) & " "& a (2) End Sub Sub FlipFirstTwo(ByRef a() As Integer) 'Swap first two elements a(1) = a(0) a(0) = a(1) End Sub |
Suppose an array has been declared in the Declarations section of the Code window with the statement Dim scores(50) As Double and numbers assigned to the elements having subscripts 0 to 50 by the frmOrder_Load event procedure. In Exercises 15 through 18, write a procedure to perform the stated task.
15. | Determine whether the array is in ascending order. |
16. | Determine whether the array is in descending order. |
17. | With a single loop, determine whether the array is in ascending order, descending order, both, or neither. |
18. | Assuming that the array is in ascending order, determine how many numbers appear more than once in the array. |
In Exercises 19 and 20, suppose arrays a(), b(), and c() are class-level and that arrays a() and b() have each been assigned 20 numbers in ascending order (duplications may occur) by a frmNumbers_Load event procedure. For instance, array a() might hold the numbers 1,3,3,3,9,9....
19. | Write a procedure to place all the 40 numbers from arrays a() and b() into c() so that c() is also in ascending order. The array c() could contain duplications. |
20. | Write a procedure to place the numbers from a() and b() into c() so that c() also has ascending order, but contains no duplications. |
21. | Write a program to declare an array with the statement Dim state(49) As String and maintain a list of certain states. The list of states should always be in alphabetical order and occupy consecutive elements of the array. The buttons in the program should give the user the following options:
|
22. | Write a program that requests a sentence one word at a time from the user and then checks whether the sentence is a word palindrome. A word palindrome sentence reads the same, word by word, backward and forward (ignoring punctuation and capitalization). An example is "You can cage a swallow, can't you, but you can't swallow a cage, can you?" The program should hold the words of the sentence in an array and use procedures to obtain the input, analyze the sentence, and declare whether the sentence is a word palindrome. (Test the program with the sentences, "Monkey see, monkey do." and "I am; therefore, am I?") |
23. | Write a program to display the average score and the number of above-average scores on an exam. Each time the user clicks a "Record Score" button, a grade should be read from a text box. The average score and the number of above-average scores should be displayed in a list box whenever the user clicks on a "Display Average" button. (Assume that the class has at most 100 students.) Use a function to calculate the average and another function to determine the number of above average scores. Note: Pass the functions an array argument for the grades and a numeric argument for the number of elements of the array that have been assigned values. |
24. | Suppose that an array of 100 names is in ascending order. Write a procedure to search for a name input by the user. If the first letter of the name is found in N through Z, then the search should begin with the 100th element of the array and proceed backward. |
25. | At the beginning of 1990, a complete box of Crayola crayons had 72 colors (in the file PRE1990COLORS.TXT). During the 1990's, 8 colors were retired (in the file RETIREDCOLORS.TXT) and 56 new colors were added (in the file ADDEDCOLORS.TXT). Each of the three files is in alphabetical order. Write a program that reads the text files into the arrays colors(), retired(), and added(), and then uses the arrays retired() and added() to update the array colors() so that it contains the current 120 colors. |
1. | Yes, provided each element of the array has the same value. |
2. | The third Case tests for duplicates and assigns only one array element to the third array if duplicates are found in the two arrays. Thus, we remove the third Case and change the first Case so it will process any duplicates. A situation where you would want to merge two lists while retaining duplications is the task of merging two ordered arrays of test scores. Select Case list1(m) Case Is <= list2(n) newList(r) = list1(m) m += 1 Case Is > list2(n) newList(r) = list2(n) n += 1 End Select |