Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Instantiate a generic variable using string class name

Tags:

java

csv

generics

I'm using google's CSVReader which requires a class name to create a parser. Using the parser, I'm reading a CSV file into a list.

Consider this code:

ValueProcessorProvider provider = new ValueProcessorProvider();
    CSVEntryParser<A> entryParser = new AnnotationEntryParser<A>(A.class, provider);

    CSVReader<A> newExternalFileCSVReader = 
            new CSVReaderBuilder<A>(m_NewExternalFile).entryParser((CSVEntryParser<A>) entryParser).strategy(new CSVStrategy(',', '"', '#', true, true)).build();
    List<A> m_NewExternalFileData = newExternalFileCSVReader.readAll();

With this code, I can read a CSV file that is specific to class A.
I have several other classes: B,C,D, which all uses the same code above, just with their respective class.

Can there be a function where I'll pass the class name as String which can instantiate a CSVReader / parser's based on the String input name? where instead of having to create 3 different code sections (for classes B,C,D), I can use the same one, just input the relevant class name?

like image 788
ocp1000 Avatar asked Feb 08 '23 11:02

ocp1000


1 Answers

You can use a factory pattern.

Create an interface and define inside the base methods for A, B, C and D.

Then all A, B, C and D classes must implements that interface.

public interface BaseInterface {
    // your methods
}

Then create a Factory class in which you pass an identifier and it will return your reader properly initiated

package a;

public final class Factory {

    // Not instantiable
    private Factory() {
        throw new AssertionError("Not instantiable");
    }

    public static CSVReader<your interface> getReader(String reader) {

        if ("A".equals(reader)) {
            return new CSVReader<A>();
        } else if ("B".equals(reader)) {
            return new CSVReader<B>();
        }
        // TODO create all your readers
    }
}

Now, you can call the reader through your factory class like this:

ValueProcessorProvider provider = new ValueProcessorProvider();
    CSVEntryParser<A> entryParser = new AnnotationEntryParser<A>(A.class, provider);

    CSVReader<your interface> newExternalFileCSVReader = 
            Factory("your reader type");
    List<your interface> m_NewExternalFileData = newExternalFileCSVReader.readAll();

As you did not post the A, B, C and D classes you have to customize that code, but following that way I think you can accomplish what you want.

like image 138
Francisco Hernandez Avatar answered Feb 15 '23 05:02

Francisco Hernandez