CISC 3130
Data Structures
Overview of Data Structures

Topics

Data Structures

From Wikipedia:

In computer science, a data structure is a data organization, management, and storage format that is usually chosen for efficient access to data. More precisely, a data structure is a collection of data values, the relationships among them, and the functions or operations that can be applied to the data.

Is an int or double a Data Structure?

Is a Student, BankAccount, or Customer Class a Data Structure?

Containers

Again, from Wikipedia:
In computer science, a container is a class or a data structure whose instances are collections of other objects. In other words, they store objects in an organized way that follows specific access rules.
Thus, a course in data structures is typically an investigation into containers.

In some sense, this course is your first in studying computer science rather than simply a programming language. We will be taking most of the material you have covered in the previous courses and applying it to the study, design, and implementation of containers.

So an Array Must be a Container and a Data Structure

Arrays

Before we move on from the built-in array, let's examine it's basic properties, operations, and limitations. Specific to Java:

Arrays in Java

A Class Version of Java's Array

Here is the Java built-in array, implemented as a class. The idea here is:
class Array {
	Array(int capacity) {arr = new int[capacity];}
	Array() {this(DEFAULT_CAPACITY);}

	int get(int index) {return arr[index];}

	void set(int index, int value) {arr[index] = value;}

	int length() {return arr.length;}

	public String toString() {
		String result = "{";
		for (int i = 0; i < length(); i++)
			result += arr[i] + (i < length()-1 ? ", " : "");
		result += "}";
		return result;
	}

	int [] arr;
	static final int DEFAULT_CAPACITY = 10;
}
Notes

A Demo App for the Array Class

Here is a Java application (i.e., a class with a main method that uses the Arrayy class defined above:
public class ArrayApp {
	public static void main(String [] args) {
		Array a = new Array();
		System.out.println("length: " + a.length());

		for (int i = 0; i < a.length(); i++)
			a.set(i, i * 10);
		System.out.println("a: " + a);
		System.out.println("length: " + a.length());

		for (int i = 0; i < a.length(); i++)
			a.set(i, a.get(i)+1);
		System.out.println("a: " + a);
	}
}
Notes
Here is the output of the app:
length: 10
a: {0, 10, 20, 30, 40, 50, 60, 70, 80, 90}
length: 10
a: {1, 11, 21, 31, 41, 51, 61, 71, 81, 91}

A First Container: Vector (Partially Populated Array)

Arrays are typically populated by reading in (or calculating) data items and adding them to the end of the array. To solve this problem, we usually employ partially-populated arrays rather than an array of the exact number of elements (i.e., a fully-populated array). The above behavior is a subset of a more substantial container known as a vector, list, or sequence (In Java, the corresponding class is the ArrayList. We will be investigating it in more detail later.

Physical and Logical Size (Capacity vs Size)

Vector Version 1: Static (Compile-time) Capacity

We're actually going to take a step backwards here vis-a-vis the above Array class: we're going to start of with a container whose capacity is hardcoded into the class (rather than specified in the constructor as we did with Array).
class Vector {
	int get(int index) {return arr[index];}

	void set(int index, int value) {arr[index] = value;}

	void add(int value) {arr[size++] = value;}

	int size() {return size;}

	public String toString() {
		String result = "{";
		for (int i = 0; i < size; i++)
			result += arr[i] + (i < size-1 ? ", " : "");
		result += "}";
		return result;
	}

	int [] arr = new int[CAPACITY];
	int size = 0;
	static final int CAPACITY = 10;
}
Notes

Here is the app:

public class VectorApp {
	public static void main(String [] args) {
		Vector v = new Vector();
		System.out.println("size: " + v.size());

		for (int i = 0; i < Vector.CAPACITY; i++) {
			v.add(i * 10);
			System.out.println(v + " (" + v.size() + ")");
		}

		for (int i = 0; i < v.size(); i++)
			v.set(i, v.get(i)+1);
		System.out.println("v: " + v);
	}
}
Notes
size: 0
{0} (1)
{0, 10} (2)
{0, 10, 20} (3)
{0, 10, 20, 30} (4)
{0, 10, 20, 30, 40} (5)
{0, 10, 20, 30, 40, 50} (6)
{0, 10, 20, 30, 40, 50, 60} (7)
{0, 10, 20, 30, 40, 50, 60, 70} (8)
{0, 10, 20, 30, 40, 50, 60, 70, 80} (9)
{0, 10, 20, 30, 40, 50, 60, 70, 80, 90} (10)
v: {1, 11, 21, 31, 41, 51, 61, 71, 81, 91}
Notes

Vector Version 2: Dynamic (Runtime) Capacity

class Vector {
	Vector(int capacity) {arr = new int[capacity];}
	Vector() {this(DEFAULT_CAPACITY);}

	int get(int index) {return arr[index];}

	void set(int index, int value) {arr[index] = value;}

	void add(int value) { arr[size++] = value;}

	int getCapacity() {return arr.length;}
	int size() {return size;}

	public String toString() {
		String result = "{";
		for (int i = 0; i < size; i++)
			result += arr[i] + (i < size-1 ? ", " : "");
		result += "}";
		return result;
	}

	int [] arr;
	int size = 0;
	static final int DEFAULT_CAPACITY = 10;
}
Notes
The app:
public class VectorApp {
	public static void main(String [] args) {
		doIt(new Vector(5));
		System.out.println();
		doIt(new Vector());
	}

	static void doIt(Vector v) {
		System.out.println("capacity: " + v.getCapacity());
		System.out.println("size: " + v.size());

		for (int i = 0; i < v.getCapacity(); i++) {
			v.add(i * 10);
			System.out.println(v + " (" + v.size() + ")");
		}

		for (int i = 0; i < v.size(); i++)
			v.set(i, v.get(i)+1);
		System.out.println("v: " + v);
	}
Notes
And the output:
capacity: 5
size: 0
{0} (1)
{0, 10} (2)
{0, 10, 20} (3)
{0, 10, 20, 30} (4)
{0, 10, 20, 30, 40} (5)
v: {1, 11, 21, 31, 41}

capacity: 10
size: 0
{0} (1)
{0, 10} (2)
{0, 10, 20} (3)
{0, 10, 20, 30} (4)
{0, 10, 20, 30, 40} (5)
{0, 10, 20, 30, 40, 50} (6)
{0, 10, 20, 30, 40, 50, 60} (7)
{0, 10, 20, 30, 40, 50, 60, 70} (8)
{0, 10, 20, 30, 40, 50, 60, 70, 80} (9)
{0, 10, 20, 30, 40, 50, 60, 70, 80, 90} (10)
v: {1, 11, 21, 31, 41, 51, 61, 71, 81, 91}