← ppnm

Exercise "generic list"

Tasks

  1. Build a simple class that implements a generic list (a list that can hold items of any given type (all items must be of the same type though)). The list must be able to grow, that is it must be possible to add items to the list (unlike arrays which can not).

    Basically only one method, "add", is needed. Something like

    public class genlist<T>{
    	public T[] data;
    	public int size => data.Length; // property
    	public T this[int i] => data[i]; // indexer
    	public genlist(){ data = new T[0]; }
    	public void add(T item){ /* add item to the list */
    		T[] newdata = new T[size+1];
    		System.Array.Copy(data,newdata,size);
    		newdata[size]=item;
    		data=newdata;
    	}
    }
    
    Suppose you have an input file with a table of numbers separated by blanks and/or tabs, like this
    129.24 24.8             4.847
    		88.6   33.745 7.78
    30.39  99.811              6.723
        -1.33   96.3   2.23
    
    Create a Main function that reads such a table from the standard input into a genlist<double[]> and the prints the table into standard output in exponential format. Something like
    var list = new genlist<double[]>
    char[] delimiters = {' ','\t'};
    var options = StringSplitOptions.RemoveEmptyEntries;
    for(string line = ReadLine(); line!=null; line = ReadLine()){
    	var words = line.Split(delimiters,options);
    	int n = words.Length;
    	var numbers = new double[n];
    	for(int i=0;i<n;i++) numbers[i] = double.Parse(words[i]);
    	list.add(numbers);
           	}
    for(int i=0;i<list.size;i++){
    	var numbers = list[i];
    	foreach(var number in numbers)Write($"{number : 0.00e+00;-0.00e+00} ");
    	WriteLine();
            }
    

  2. (Extra) Implement "void remove(int i)" method that removes element number "i".

  3. (Extra) Improve the speed of the "add" method by increasing the capacity of the data-array not by one element, but instead by doubling it. That should decrease the amount of array copying significantly for the price of increased memory usage. Something like

    public class genlist<T>{
    	public T[] data;
    	public int size=0,capacity=8;
    	public genlist(){ data = new T[capacity]; }
    	public void add(T item){ /* add item to list */
    		if(size==capacity){
    			T[] newdata = new T[capacity*=2];
    			System.Array.Copy(data,newdata,size);
    			data=newdata;
    			}
    		data[size]=item;
    		size++;
    	}
    }
    

  4. (Extra) Implement generic list using a chain of nodes,

    public class node<T>{
    	public T item;
    	public node<T> next;
    	public node(T item){this.item=item;}
    }
    
    Something like this,
    public class list<T>
            public node<T> first=null,current=null;
            public void add(T item){
                    if(first==null){
                            first=new node<T>(item);
                            current=first;
                    }
                    else{
                            current.next = new node<T>(item);
                            current=current.next;
                    }
            }
            public void start(){ current=first; }
            public void next(){ current=current.next; }
    }
    public class main{
            public static void Main(){
                    list<int> a = new list<int>();
                    a.add(1);
                    a.add(2);
                    a.add(3);
                    for( a.start(); a.current != null; a.next()){
                            WriteLine(a.current.item);
                    } } }