Search Unity

Problem with ArrayPrefs / arrays

Discussion in 'Scripting' started by Zwiebel, Jul 27, 2015.

  1. Zwiebel

    Zwiebel

    Joined:
    Jul 23, 2013
    Posts:
    56
    Hi!

    I'm developing a game, which would have buy-able characters. I would like to store the bought characters as an int in an array, so I could get them from it easily. As Unity doesn't provide array saving to playerprefs, I have looked for a solution and found ArrayPrefs2. It is working well in basic, but when I add a new character to the game it is fail to work properly, while I won't delete playerprefs, which is not a perfect way to update an app...

    Every start in the menu I call
    Code (csharp):
    1.      charactersBought = PlayerPrefsX.GetIntArray("charactersBought", 0, maxCharacters + 1);  
    and here is the problem as I would like to modify the charactersBought variable's size in the inspector when I add new characters to the game. Is it not possible as the first start the game save the array's size to the charactersBought variable so if I update the app the user will get exceptions, and wouldn't be able to see the new characters. Now I have found a workaround but I don't know how much memory would a 200-300 sized int array allocate, and if it is a "doable" workaround. I would give the array a big number for example 300 but I only would like to have for example 30 characters at first.

    Will it be a problem with the memory on 4-5 years old devices with 512 MB ram? Will it cause performance problems?
     
  2. DonLoquacious

    DonLoquacious

    Joined:
    Feb 24, 2013
    Posts:
    1,667
    You can store the data in your game as a list, and then just convert it to an array when it comes time for saving. When you import it back in, make a temporary array of the size you need, import the data into it, then turn that into a list for use in the game again.

    Alternatively, you really don't need that ArrayPrefs2 script. If you're converting it anyways, you may as well just save the data directly from a list, rather than back and forth as an array in the middle. Just save the number of items and string name of the list to the prefs (as normal), then iterate over the list and save each item to PlayerPrefs individually with a string identifier that increments too (like "listitem1", "listitem2", etc...). Loading is just doing that in reverse, and because it's a list you don't have to worry about setting the maximum length or anything.

    Arrays have a lot of fantastic uses, but managing dynamically sized datasets isn't really one of them.
     
  3. Eric5h5

    Eric5h5

    Volunteer Moderator Moderator

    Joined:
    Jul 19, 2006
    Posts:
    32,401
    Just use generic Lists and convert to/from arrays when using ArrayPrefs. (The large overhead of saving each item to a separate PlayerPrefs is one of the things ArrayPrefs is for, since PlayerPrefs really isn't suitable for large amounts of data.) Anyway, 300 is far from a "big number" for an int array. I'd recommend reading up on data types and memory usage.

    --Eric
     
  4. Zwiebel

    Zwiebel

    Joined:
    Jul 23, 2013
    Posts:
    56
    Thank you for the answers! I have read on the data types a bit and I have found that an int is 2 byte and and an array is needed 20 byte for the initialization + 4 byte per dimension. So for example if I make a 200 sized array that would "only" take 200*2 + 20 + 4 bytes?
     
  5. Eric5h5

    Eric5h5

    Volunteer Moderator Moderator

    Joined:
    Jul 19, 2006
    Posts:
    32,401
    An int is 4 bytes; a short is 2 bytes. 200*4 + a few bytes overhead < 1KB and therefore trivial. But you should still use List instead, and convert to/from arrays when using ArrayPrefs.

    --Eric
     
  6. Zwiebel

    Zwiebel

    Joined:
    Jul 23, 2013
    Posts:
    56
    Thank you will take a look at lists, as I haven't used them before.