Search code examples
javasingletonbluejconstructor-overloadingprivate-constructor

trouble instantiating a singleton overloaded constructor -Error: constructor in type cannot be applied to given types


I am using the GoPiGo3 class from GautamV/J4GPG on github to control a GoPiGo3 board from DexterIndustries. The code is not official from DexterIndustries but a java port from a python library that DexterIndustries makes.

I am just trying to test the code and cant create an instance of the GoPiGo3 class. I am using BlueJ, made a package of GautamV's code in BlueJ, and imported the GoPiGo3 class into a demo class.

My research leads me to believe that the GoPiGo3 class is designed as a singleton to ensure that only one instance is ever created and has overloaded constructors to allow for flexibility in its instantiation.

Here is relevant code from the GoPiGo class:


    private static GoPiGo3 _instance; 

    public static GoPiGo3 Instance() throws IOException, FirmwareVersionException{
        if (_instance == null) {
            _instance = new GoPiGo3(8, true);
        }
        return _instance;
    }

    public static GoPiGo3 Instance(int addr) throws IOException, FirmwareVersionException{
        if (_instance == null) {
            _instance = new GoPiGo3(addr, true);
        }
            return _instance;
    }

    public static GoPiGo3 Instance(boolean detect) throws IOException, FirmwareVersionException{
        if (_instance == null) {
            _instance = new GoPiGo3(8, detect);
        }
        return _instance;
    }

    public static GoPiGo3 Instance(int addr, boolean detect) throws IOException, FirmwareVersionException{
        if (_instance == null) {
            _instance = new GoPiGo3(addr, detect);
        }
        return _instance;
    }

    private GoPiGo3(int addr, boolean detect) throws IOException, FirmwareVersionException {
        SPIAddress = addr;
        spi = SpiFactory.getInstance(SpiChannel.CS1, // Channel 1
                500000, // 500 kHz
                SpiMode.MODE_0); // Mode 0
        if (detect) {
            //does detect stuff
        }

The expected result is an initialized object of the GoPiGo3 class. Code currently does not compile. The GoPiGo class compiles without error, but the Demo class that is attempting to initialize GoPiGo class does not.

My attempts at instantiation are

GoPiGo3 platform = new GoPiGo3();

That leads to the following error:

Constructor GoPiGo3 in class com.j4gpg3.control.GoPiGo3 cannot be applied to given types: required: int.boolean
found:no arguments
reason: actual and formal argument lists differ in length The operator that you use here cannot be used for the type of value that you are using it for. You are either using the wrong type here, or the wrong operator.

When I try:

GoPiGo3 platform = new GoPiGo3(8,true);

That leads to the following error:

GoPiGo3(int,boolean) has private access in com.j4gpg3.control.GoPiGo3


Solution

  • As you said, its implemented using a singleton pattern, so you need to use the Instance methods instead of constructor. Because of the private modifier on constructor private GoPiGo3(int addr, boolean detect)..., it can only be called from within GoPiGo3 class.

    public static GoPiGo3 Instance() throws IOException, FirmwareVersionException{
        if (_instance == null) {
            _instance = new GoPiGo3(8, true);
        }
        return _instance;
    }
    
    public static GoPiGo3 Instance(int addr) throws IOException, FirmwareVersionException{
        if (_instance == null) {
            _instance = new GoPiGo3(addr, true);
        }
            return _instance;
    }
    
    public static GoPiGo3 Instance(boolean detect) throws IOException, FirmwareVersionException{
        if (_instance == null) {
            _instance = new GoPiGo3(8, detect);
        }
        return _instance;
    }
    
    public static GoPiGo3 Instance(int addr, boolean detect) throws IOException, FirmwareVersionException{
        if (_instance == null) {
            _instance = new GoPiGo3(addr, detect);
        }
        return _instance;
    }
    

    To get the GoPiGo3 instance, you need to do:

    GoPiGo3 platform = GoPiGo3.Instance(8,true);
    

    Reference:

    https://www.geeksforgeeks.org/singleton-class-java/