non-static variable this cannot be referenced in a static context in Java

I don't understand why does this code give me issues since I am declaring new instances within the outclass.

Here is my solution for the problem (UvA-103): 103-StackingBoxes.

Originally I was getting runtime errors of NullPointerExceptions:

C:\Users\User\Desktop\103-StackingBoxes>java
Main
5 2

Exception in thread "main" java.lang.NullPointerException
        at Main.main(Main.java:27)

I fixed that, but now I am getting the following compilation error:

C:\Users\User\Desktop\103-StackingBoxes>javac
 Main.java
Main.java:28: error: non-static variable this cannot be referenced from a static
 context
                                boxArray[i] = new box();
                                              ^
1 error

I know inner classes are typically avoided in Java, but I do not get why in particular do my statements not work.

import java.util.*;
import java.io.*;
//import java.util.Arrays;

public class Main
{

    public static void main(String args[])
    {

        Scanner input = new Scanner(System.in);
        int k,n;

        while(input.hasNext())
        {
            System.out.printf("\n");
            k = input.nextInt();
            n = input.nextInt();

            // box boxArray[] = new box(n)[k];
            box[] boxArray = new box[k];

            for(int i =0; i< k; i++)
            {
                boxArray[i] = new box();
                //boxArray[i] = boxArray[i].box(n);
                boxArray[i].totalDim = n;
                for(int j =0; j < n; j++)
                {
                    boxArray[i].dimensions[j]=input.nextInt();
                }
            }


            boxArray = sortBoxArray(boxArray);

            int count = 1;
            for(int i =k-1; i > 1 ; i--)
            {
                if(boxArray[i].doesArgBoxFitInside(boxArray[i-1]))
                    count++;
                else
                    break;
            }

            System.out.printf("%d\n",count);
            for(int i = k-count; i < k ; i++)
            {
                if(i == k-1)
                    System.out.printf("%d",boxArray[i].placeNumber);
                else
                    System.out.printf("%d ",boxArray[i].placeNumber);
            }


        }

    }

    public static box[] sortBoxArray(box[] boxArray)
    {
        for(int i = 1; i < boxArray.length; i++)
        {
            for(int j = boxArray.length-1; j>=i; j++)
            {
                boolean skip = false;
                for(int k = 0; k < boxArray[j].totalDim; k++)
                {
                    if(boxArray[j].dimensions[k]<boxArray[j].dimensions[k-1])
                    {
                        box temp = boxArray[j-1];
                        boxArray[j-1] = boxArray[j];
                        boxArray[j]=temp;
                    }   
                }
            }
        }

        return boxArray;
    }


    public class box{

        /*******************************************Fields***********************************************/
        public int totalDim;
        public int dimensions[];
        //The field I forgot about
        public int placeNumber;

        /*******************************************Methods**********************************************/
        public box()
        {
            this.totalDim = -1;
            this.dimensions= new int[0];
            this.placeNumber = -1;
        }

        public box(int totalDim)
        {
            this.totalDim = totalDim;
            this.dimensions = new int[totalDim];
        }

        //public box(int totalDim, int[totalDim] dimensions)
        public box(int totalDim, int[] dimensions)
        {
            this.totalDim = totalDim;
            this.dimensions = dimensions;
            sortDim();

        }

        public void sortDim()
        {
            Arrays.sort(dimensions);        
        }

        public boolean doesArgBoxFitInside(box wop)
        {
            if(this.totalDim != wop.totalDim)
                return false;
            else
            {
                for(int i =0; i < totalDim; i++)
                {
                    if(this.dimensions[i]<wop.dimensions[i])
                        return false;
                }
                return true;
            }
        }
    }   
}

Answers


Your class box (please stick to Java's coding conventions of uppercase class names!) is an inner class and not visible for your static code:

"An instance of InnerClass can exist only within an instance of OuterClass and has direct access to the methods and fields of its enclosing instance. To instantiate an inner class, you must first instantiate the outer class. Then, create the inner object within the outer object with this syntax: OuterClass.InnerClass innerObject = outerObject.new InnerClass();" (http://docs.oracle.com/javase/tutorial/java/javaOO/nested.html).


Problem is: Your box class is inner class of Main class, As pointed by @Smutje that inner class is not visible to static method. Reason for this is: static method can be executed even if there is no instance of class and inner class object can only exist if there is object of outer class, so both statement are sort of contradictory. Hence, inner class is not made directly accessible in static method.

Fix:

Either you can make Box class as static or you can make an instance of Box class after making object of outer class.

Code for second solution:

    Main obj = new Main();
    for(int i =0; i< k; i++)
    {
        boxArray[i] = obj.new box();

Need Your Help

How to do a git diff on moved/renamed file?

git diff file-rename mv

I moved a file using git mv. Now I would like to do a diff on the new file to compare it with the old file (with the old, now non-existent name).

Prevent checkbox from unchecking when clicked (without disable or readonly)

javascript jquery events checkbox

I'm using a checkbox and I want people to be able to check/uncheck it.