0

I am working with the Spigot API (for Minecraft plugins). When saving configurations, there is an option to save a List < Map< ?, ? > >. So that data structure would look like:

Item

  • Key : Value
  • Key : Value
  • Key : Value

I want to be able to save configuration information related to specific users. What I want is a data structure that looks like this:

Users

  • User1
    • Setting 1 : Value
    • Setting 2 : Value
  • User2
    • Setting 1 : Value
    • Setting 2 : Value
  • User3
    • Setting 1 : Value
    • Setting 2 : Value

The code that I have been writing is utterly disgusting. I've made it more readable by removing the wildcards, but here it is:

    List<Map<String, Map<String, String>>> users = new ArrayList<Map<String, Map<String, String>>>();

    Map<String, Map<String, String>> justin = new HashMap<String, Map<String, String>>() {{}};

    for (Map<String, String> config : justin.values()) {
        config.put("key1", "value1");
        config.put("key2", "value2");
        config.put("key3", "value3");
    }

    Map<String, Map<String, String>> not_justin = new HashMap<String, Map<String, String>>() {{}};

    for (Map<String, String> config : not_justin.values()) {
        config.put("key1", "value1");
        config.put("key2", "value2");
        config.put("key3", "value3");
    }

    users.add(justin);
    users.add(not_justin);
}

When I try to print this, I recieve this as an output:

[{}, {}]

I have tried iterating through everything, and still don't get any actual values. So my two questions are

a) is there a simpler way to do this that I'm forgetting about

b) if there isn't, why isn't my code printing?

Thank you,

Justin

Schwaitz
  • 473
  • 3
  • 12
  • 1
    a) You can make your code cleaner by using [diamond notation](https://docs.oracle.com/javase/tutorial/java/generics/types.html#diamond). b) Why are you constructing with empty initialization blocks (`{{}}`)? c) `justin` and `not_justin` are both empty. Why would you expect your loops to do anything? – shmosel Oct 16 '16 at 07:47
  • @shmosel, a) the only way to initialize a HashMap is by initializing it as a new class that inherits HashMap b) config is set to justin.values() which (according to the JavaDocs) uses the HashMap backend, so changes made to that will change 'justin' itself – Schwaitz Oct 16 '16 at 07:50
  • If you're referring to [double-brace initialization](http://stackoverflow.com/questions/1958636/what-is-double-brace-initialization-in-java), you're not doing any initialization, so it's pointless. Besides, it's not the "only" way, or even the recommended way. – shmosel Oct 16 '16 at 07:52
  • 1
    `config` would reference each value in turn in `justin` if it weren't empty. But in this case, `justin` is empty, so the loop is a no-op. – shmosel Oct 16 '16 at 07:53
  • 1
    I figured it out: I am an idiot who made a simple mistake. I iterated over the values of 'justin' when there were none. Pardon my idiocy. – Schwaitz Oct 16 '16 at 07:54
  • Also, I was using wildcards, but changed them to values to make it easier to read – Schwaitz Oct 16 '16 at 07:54
  • The fact that a library uses a wildcard type just means that they can accept a `Map` with any type parameter. It doesn't mean you should be using wildcards for your variables, or you're in for a lot of ugly casting. – shmosel Oct 16 '16 at 07:58
  • 1
    As far as cleanliness goes, it seems you're trying to do too much with data structures. Why not have a `User` class with a configuration map? – ChiefTwoPencils Oct 16 '16 at 07:58
  • @ChiefTwoPencils mostly because of the way I'm passing it to the library – Schwaitz Oct 16 '16 at 07:59
  • @Schwaitz Isn't the API as per your question is expecting List> If that is the case as per ChiefTwoPencils, I think User class could be a better fit and would make your code lot more modularised and a lot more readable. Any particular reason as why you are passing using String as the only type to the API? – Kamal Kunjapur Oct 16 '16 at 08:34
  • Just putting it out there (don't hate) : what about user specific Config files? Or when you say user you actually mean "player" and the same OS user is used? – Shay Nehmad Oct 16 '16 at 09:12
  • @ShayNehmad They are attached to usernames, so I hypothetically could. I've just never seen it done like that before, ever. – Schwaitz Oct 16 '16 at 20:38
  • @Schwaitz it is done all the time, very useful and cross platform - in Windows it's under c:/users/user/.appdata and in Linux it is /usr (I think). – Shay Nehmad Oct 16 '16 at 20:46
  • @ShayNehmad are you talking specifically about the spigot API that I am using, or Java in general? – Schwaitz Oct 16 '16 at 20:47
  • @Schwaitz configuration management in general. – Shay Nehmad Oct 16 '16 at 20:50
  • @ShayNehmad I am using the word "library" liberally for the sake of explaining my problem. The code only has access to the file system within the folder that the compiled jar file is placed. That's why I'm doing it the way I am - and why it is even relatively annoying. – Schwaitz Oct 16 '16 at 20:58

0 Answers0