Search code examples
javaclassstatic

Java Better way to create memory efficient static methods


I have a class Repo with following definition:

class Repo
{
    private final record Table(String name,List<String[]> columns){}
    private static final Map<Integer,Table> TABLES = Map.ofEntries(
        Map.entry(0, new Table("item 1", List.of(
                                                 new String[]{"A","B","C"},
                                                 new String[]{"AA","BB","CC"},
                                                 //... Long list of String[]
                                                 ))),
        Map.entry(1, new Table("item 2", List.of(
                                                 new String[]{"D","E","F"},
                                                 new String[]{"DD","EE","FF"},
                                                 //... Long list of String[]
                                                 ))),
        //... More entries
    );

    protected static String getTableName(int index)
    {
        return TABLES.get(index).name();
    }
    
    private static List<String[]> getColumns(int index)
    {
        return TABLES.get(index).columns();
    }
    protected static String initTables(int index)
    {
        var table = getTableName(index);
        var columns = getColumns(index).append(",");
        var builder = new StringBuilder(table).append(",")
        for(var col: columns)
        {
            builder.append(col[0]).append(",").append(col[1]).append(",").append(col[2]);
        }
        return builder.toString();
    }
}

My question is, The initTables function is called only once by another method connect() which itself resides in a class Model whose scope is throughout the program life, whereas getTableName will be called numerous times by various methods. Since the TABLES and initTables are static, they'll remain in the memory throughout the program. is there any way to remove them from space once they are done?

I thought of creating a separate class for TABLES called TableColumns having only columns and create its instance in the initTables:

class Repo
{
private static final Map<Integer,String> TableNames = Map.ofEntries(
    Map.entry(0, "item 1"),
    Map.entry(1, "item 2"),
    //... more entries
);

protected String getTableName(int index)
{
    return TABLES.get(index);
}

protected String initTables(int index)
{
    var table = getTableName(index);
    var builder = new StringBuilder(index).append(",");
    var tablecolumns = new TableColumns().getColumns(index);
    for(var col:tablecolumns)
    {
        ...
    }
    return builder.toString();
}
}

TableColumns class

public TableColumns
{
    private static final Map<Integer,List<String[]>> TABLES = Map.ofEntries(
        Map.entry(0, List.of(
                             new string[]{...},
                             //... more String[]
        )),
        //... more entries
    );
    
    public TableColumns(){}
    protected List<String[]> getColumns(int index)
    {
        return TABLES.get(index);
    }
}

Will this optimize memory usage or is there any better way of achieving this?


Solution

  • As suggested by Thomas Klager, I turned the item1, item2 etc. entries into external text files, and modified initTables as such:

    protected String initTables(int index)
    {
        var tableName=getTableName(index);
        try(var scanner=new Scanner(getClass().getResourceAsStream(tableName))
        {
            while(scanner.hasNextLine())
            {
                System.out.println(scanner.nextLine());
            }
        }
    }