Search code examples
javalistspace

Why does my adjacency list contain a blank space? (Java)


My code creates and prints an adjacency list from a given text file, however when printing out it leave a blank space after the second node for whichever input file I use. Here's the main part of the code:

class Neighbor {
    public int vertexNum;
    public Neighbor next;
    public Neighbor(int vnum, Neighbor nbr) {
            this.vertexNum = vnum;
            next = nbr;
    }
}

class Vertex {
    String name;
    Neighbor adjList;
    Vertex(String name, Neighbor neighbors) {
            this.name = name;
            this.adjList = neighbors;
    }
}


public class Graph 
{

    static Vertex[] adjLists;

    public Graph(String file) throws FileNotFoundException 
    {
        Scanner fileScanner = new Scanner(new File(file));
        fileScanner.useDelimiter("[^A-Za-z0-9]");


        ArrayList<String> words = new ArrayList<String>();

        while (fileScanner.hasNext())
        {
            String nextWord = fileScanner.next();
            if (!words.contains(nextWord))
            {
                words.add(nextWord);
            }
        }

        adjLists = new Vertex[words.size()];

        // read vertices
        for (int v=0; v < adjLists.length; v++) 
        {
            adjLists[v] = new Vertex(words.get(v), null);
        }

        // read edges
        Scanner sc = new Scanner(new File(file));

        while (sc.hasNext()) 
        {
             // read vertex names and translate to vertex numbers
            int v1 = indexForName(sc.next());
            int v2 = indexForName(sc.next());

            // add v2 to front of v1's adjacency list and
            // add v1 to front of v2's adjacency list
            adjLists[v1].adjList = new Neighbor(v2, adjLists[v1].adjList);
            // Doesn't add the node twice if it's connected to itself
            if(v1!=v2) {
         adjLists[v2].adjList = new Neighbor(v1, adjLists[v2].adjList);
            }
        }         
    }

    int indexForName(String name) 
    {
        for (int v=0; v < adjLists.length; v++) {
            if (adjLists[v].name.equals(name)) {
                return v;
            }
        }
        return -1;
    }   

    public void print() 
    {
        System.out.println();
        for (int v=0; v < adjLists.length; v++) {
            System.out.print(adjLists[v].name);
            for (Neighbor nbr=adjLists[v].adjList; nbr != null;nbr=nbr.next) {
                System.out.print(" --> " + adjLists[nbr.vertexNum].name);
            }
            System.out.println("\n");
        }


    }

Here is the example output:

Sara --> Ajay --> Sam

Sam --> Mira --> Sean --> Sara



Ajay --> Sara

Sean --> Sam
etc.

Why does this gap between Sam and Ajay exist? No matter how long the list is, or what file I use, there is always a gap between the 2nd and 3rd node, and when running analysis on the list it has an effect because it is essentially reading a blank line and counting it as a node. This doesn't happen anywhere else in the list, just after the second node.

My input data looks like this

Sara Sam
Sara Ajay
Sam Sean
Sam Mira
Mira Jane
etc.

Calling print:

Scanner br = new Scanner(System.in);
System.out.print("Enter graph input file name: ");
String file = br.nextLine();
Graph graph = new Graph(file);
graph.print();

Solution

  • If you debug your code you will see that your third element of the words ArrayList is an empty string. This is due to how the file is read and how your input is handled.

    Commenting the fileScanner.useDelimiter line provides a correct output. Otherwise you could just add the following condition:

            if (!nextWord.isEmpty() && !words.contains(nextWord)) {
                words.add(nextWord);
            }
    

    and it should be fine.