CSCI A201/A597

Lecture Notes 23

Spring 2000


Arrays: managing large quantities of data uniformly.

Arrays represent a ubiquitous data structure meant to simplify the processing of data by indexing it. If you understand the concept of variable you will have no problem understanding the concept of array.

Arrays (like variables in general) are simply ways of using the computer memory in your programs. In case of arrays you can allocate space for more than one location at a time, and refer to any of the allocated locations by the same name, and using an index.

Here are some examples to illustrate this point:

public class Apr04 {
    public static void main(String[] args) {
	int n = 12;                                 // [1] 
	int[] m;                                    // [2] 
	m = new int[n];                             // [3] 
	for (int i = 0; i < m.length; i+=1) {       // [4] 
	    System.out.println(i + ": " + m[i]);    // [5] 
	}                                           // [6] 
    } 
} 
Here's a description of this program step by step:
Here's a variation of it:
import java.util.Random; 

public class Apr04 {
    public static void main(String[] args) {
	Random rand = new Random(); 
	int n = 12; 
	int[] m; 
	m = new int[n];
	for (int i = 0; i < m.length; i+=1) {
	    m[i] = Math.abs(rand.nextInt()) % (50 - 30 + 1) + 30; 
	}
	int sum = 0;  
	for (int i = 0; i < m.length; i+=1) {
	    System.out.println(i + ". Adding: " + m[i]); 
	    sum += m[i]; 
	}
	System.out.println("The total is: " + sum); 
    } 
} 
What does it do?

Here's another one.

This time the array is of String's.

public class Apr04 {
    public static void main(String[] args) {
	String[] months;
	months = new String[12]; 
	months[0] = "Jan"; 
	months[1] = "Feb"; 
	months[2] = "Mar"; 
	months[3] = "Apr"; 
	months[4] = "May"; 
	months[5] = "Jun"; 
	months[6] = "Jul"; 
	months[7] = "Aug"; 
	months[8] = "Sep"; 
	months[9] = "Oct"; 
	months[10] = "Nov"; 
	months[11] = "Dec"; 
	for (int i = 0; i < months.length; i+=2) {
	    System.out.println(months[i]); 
	} 
    } 
} 
Where can you get an array of String's already initialized?

Exactly: from the command line.

Here's an example:

frilled.cs.indiana.edu%cat Apr04.java
public class Apr04 {
    public static void main(String[] months) {
	for (int i = 0; i < months.length; i++) {
	    System.out.println(months[i]); 
	} 
    } 
} 
frilled.cs.indiana.edu%javac Apr04.java
frilled.cs.indiana.edu%java Apr04 Jan Feb Mar Apr May Jun Jul Aug Sep 
Jan
Feb
Mar
Apr
May
Jun
Jul
Aug
Sep
frilled.cs.indiana.edu%
This particular array is built automatically by the Java run-time system for you, based on what you type on the command-line.

The array is made out of String's so if you want to look at them as numbers you need to parse the String's first.

Here's computing the sum of a sequence of numbers specified on the command line:

frilled.cs.indiana.edu%cat Apr04.java
public class Apr04 {
    public static void main(String[] months) {
	int sum = 0; 
	for (int i = 0; i < months.length; i++) {
	    int n = Integer.parseInt(months[i]);
	    sum += n; 
	} 
	System.out.println(sum); 
    } 
} 
frilled.cs.indiana.edu%javac Apr04.java
frilled.cs.indiana.edu%java Apr04
0
frilled.cs.indiana.edu%java Apr04 1 2 3
6
frilled.cs.indiana.edu%java Apr04 6 9
15
frilled.cs.indiana.edu%
Multidimensional arrays use more than one index to locate a location.

We've seen (at least conceptually) two-dimensional arrays.

Here's one, in which the elements are all char.

frilled.cs.indiana.edu%cat Apr04.java
public class Apr04 {
    public static void main(String[] args) {
	int size = Integer.parseInt(args[0]); 
	char[][] letter; 
	letter = new char[size][size]; 
	for (int i = 0; i < size; i++) {
	    for (int j = 0; j < size; j++) {
		if (i == 0 || i == size-1 || i+j == size-1) {
		    letter[i][j] = '*'; 
		} else {
		    letter[i][j] = ' '; 
		}
	    } 
	}

	for (int i = 0; i < size; i++) {
	    for (int j = 0; j < size; j++) {
		System.out.print(" " + letter[i][j]); 
	    }
	    System.out.println(); 
	} 
    } 
} 
frilled.cs.indiana.edu%javac Apr04.java
frilled.cs.indiana.edu%java Apr04
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: -1
	at Apr04.main(Compiled Code)
frilled.cs.indiana.edu%java Apr04 10
 * * * * * * * * * *
                 *  
               *    
             *      
           *        
         *          
       *            
     *              
   *                
 * * * * * * * * * *
frilled.cs.indiana.edu%
What's the difference to the method used at the first practical?

We've seen one arrays and variables being used in main.

What if we pass them as arguments to a procedure.

Will it make a difference?

Let's experiment.

Stage one: pass a variable to a method.

frilled.cs.indiana.edu%
cat Apr04.java
public class Apr04 {
    public static void main(String[] args) {
	int n; 
	n = 10; 
	System.out.println("main before addOne n is " + n); 
	Library.addOne(n); 
	System.out.println("main after addOne n is " + n); 
    } 
} 

class Library {
    public static void addOne(int n) {
	System.out.println("... addOne receives n as " + n); 
	n = n + 1;
 	System.out.println("... addOne changed n to " + n); 
    } 
} 
frilled.cs.indiana.edu%javac Apr04.java
frilled.cs.indiana.edu%java Apr04
main before addOne n is 10
... addOne receives n as 10
... addOne changed n to 11
main after addOne n is 10
frilled.cs.indiana.edu%
Can you explain what happens, step by step?

Let's do the same by passing an array.

frilled.cs.indiana.edu%cat Apr04.java
public class Apr04 {
    public static void main(String[] args) {
	System.out.println("Initializing array."); 
	int[] n = { 1, 2, 3, 4, 5, 6 }; 
	System.out.println("Printing array: "); 
	for (int i = 0; i < n.length; i++) {
	    System.out.print(n[i] + " "); 
	} 
	System.out.println(); 
	System.out.println("Calling addOne on the array."); 
	Library.addOne(n); 
	System.out.println("Back in main the array looks like this:"); 
	for (int i = 0; i < n.length; i++) {
	    System.out.print(n[i] + " "); 
	} 
	System.out.println(); 
	System.out.println("End of program."); 
    } 
} 

class Library {
    public static void addOne(int[] n) {
	System.out.println("... in addOne the array received is: "); 
	for (int i = 0; i < n.length; i++) {
	    System.out.print(n[i] + " "); 
	} 
	System.out.println(); 
	System.out.println("... now we change it to: "); 
	for (int i = 0; i < n.length; i++) {
	    n[i] += 1; 
	} 
	System.out.println(); 
	for (int i = 0; i < n.length; i++) {
	    System.out.print(n[i] + " "); 
	} 
	System.out.println(); 
	System.out.println("... and return to main."); 
    } 
} 
frilled.cs.indiana.edu%javac Apr04.java
frilled.cs.indiana.edu%java Apr04
Initializing array.
Printing array: 
1 2 3 4 5 6 
Calling addOne on the array.
... in addOne the array received is: 
1 2 3 4 5 6 
... now we change it to: 

2 3 4 5 6 7 
... and return to main.
Back in main the array looks like this:
2 3 4 5 6 7 
End of program.
frilled.cs.indiana.edu%
See the difference?

Let's finish with three small examples.

What's this one doing?

public class Apr04 {
    public static void main(String[] args) {
	int size;
	int[] n; 
	size = args.length; 
	n = new int[size]; 
	for (int i = 0; i < n.length; i++) {
	    n[i] = Integer.parseInt(args[i]); 
	} 
    } 
} 
It is allocating an array and filling it with the values received on the command line. The array inside is of the same size as the one created and passed to main by the Java run time system.

Of course, this is redundant, but a good exercise.

Computing the max.

frilled.cs.indiana.edu%cat Apr04.java
public class Apr04 {
    public static void main(String[] args) {
	int max = Integer.parseInt(args[0]); 
	for (int i = 0; i < args.length; i++) {
	    if (max < Integer.parseInt(args[i])) {
		max = Integer.parseInt(args[i]); 
	    } 
	} 
	System.out.println("Max is: " + max); 
    } 
} 


frilled.cs.indiana.edu%javac Apr04.java
frilled.cs.indiana.edu%java Apr04 -3 1 -9 2 5 -6
Max is: 5
frilled.cs.indiana.edu%
You've seen this before, hopefully it's clearer now.

It's a combination of new algorithm and new syntax, hopefully refreshing.

Let's look at arrays of Circles.

import java.util.Random; 
import element.*; 

public class Apr04 {
    public static void main(String[] args) {
	DrawingWindow d = new DrawingWindow(); 
	Random gen = new Random(); 
	int size = Integer.parseInt(args[0]); 
	Circle[] circles = new Circle[size]; 
	for (int i = 0; i < size; i++) {
	    circles[i] = new Circle(Lib.m1(gen, 30, 170), 
				    Lib.m1(gen, 30, 170), 
				    Lib.m1(gen, 20, 40)); 
	} 
	for (int i = 0; i < circles.length; i++) {
	    d.draw(circles[i]); 
	} 
    } 
} 

class Lib {
    public static int m1(Random r, int left, int right) {
	return Math.abs(r.nextInt()) % (right - left + 1) + left; 
    } 
} 
(Red squares with two-dimensional arrays: it could simplify the overall procedure).

Next step would be to move the circles with the mouse. For this we would have to fill them and also (since it's easier) use the invertMode drawing mode.


Last updated: April 4, 2000 by Adrian German