Best way to save a bunch of staff

Discussion in 'Plugin Development' started by LordManegane, Nov 7, 2013.

Thread Status:
Not open for further replies.
  1. Offline

    LordManegane

    Well. I post this because i have a plugin that saves a bunch of values to a .yml.
    The problem its that the server kick all the players while its saving the values and if i want to retrive the values of the .yml the server stops all the animations and stuff going.
    If someone could say me a better way to save values.
     
  2. Offline

    RealDope

    What?..

    If your server is freezing from saving and retrieving values from yaml, you're probably doing something wrong.
     
  3. Offline

    LordManegane

    RealDope I want to save lots of strings to a file. I want to know the best way.
     
  4. Offline

    FinalFred

    If you have massive amounts of data to save, a database is the way to go.

    That said, I agree with RealDope. It would take a lot of data getting written to freeze the main thread long enough to kick everyone off. You are probably doing something ineffectively or in a very weird way.
     
  5. Offline

    AoH_Ruthless

    LordManegane
    We can't help you until you post your code and/or your .yml (preferably both to help us). If either is long, I recommend using pastebin.
     
  6. Offline

    LordManegane

    RealDope the server freeze but before the action stop, it keeps going on normaly
     
  7. Offline

    xTrollxDudex

    LordManegane
    Please post the code... What are you doing? We don't know.
     
    Acer_Mortem likes this.
  8. Offline

    The_Doctor_123

    LordManegane
    Dang, you making a game inside of a game or what? It's likely that your code is inefficient.
     
  9. Offline

    LordManegane

    The_Doctor_123 xTrollxDudex AoH_Ruthless FinalFred Thanks to everyone for quick the quick reply.

    Saving:
    Code:java
    1.  
    2. public static void save(Player player,Location l1, Location l2,String seleccion, String path){
    3.  
    4. for(int x = minX; x <= maxX; x++){
    5. for(int y = minY; y <= maxY; y++){
    6. for(int z = minZ; z <= maxZ; z++){
    7. i++;
    8.  
    9. File pFile = new File(path);
    10. FileConfiguration pConfig = YamlConfiguration.loadConfiguration(pFile);
    11. Location l = new Location(Bukkit.getWorld(player.getWorld().getBlockAt(x,y,z).getWorld().getName()), x, y, z);
    12.  
    13. pConfig.set("y"+i, (y));
    14. pConfig.set("z"+i, (z));
    15. pConfig.set("world"+i, (player.getWorld().getName()));
    16. pConfig.set("blocks", pConfig.getInt("blocks")+1);
    17. pConfig.save(pFile);
    18. }
    19. }
    20. }
    21. }

    Loading
    Code:java
    1. public static void load(String seleccion, final CommandSender sender, String path){
    2. File pFile = new File(path);
    3. final FileConfiguration pConfig = YamlConfiguration.loadConfiguration(pFile);
    4. sender.sendMessage("Loading");
    5. for(int i = 0; i <= pConfig.getInt("blocks");i++){
    6. try{
    7.  
    8. double x = pConfig.getDouble("x"+i);
    9. double y = pConfig.getDouble("y"+i);
    10. double z = pConfig.getDouble("z"+i);
    11. String world = pConfig.getString("world"+i);
    12. Location l = new Location(Bukkit.getWorld(world),x, y, z);
    13. l.getBlock().setTypeId(1);
    14.  
    15.  
    16. }catch(Exception e){
    17. i = 0;
    18.  
    19. }
    20. }
    21. }

    Thats the code :p
     
  10. Offline

    1Rogue

    x^3 time complexity on the for loops, and saving on every iteration of the z variable? For one, move variables used throughout the method outside of the loops, and clean up whatever that is with the loops.
     
  11. Offline

    FinalFred

    Agreed with what 1Rogue said. What you're doing is parsing a file, changing a few values, and then saving a file... and you're doing that each time once for every block. That is extremely ineffecient. File operations (opening to read, opening to write, actually reading/writing) are somewhat slow. They're not actually all that slow (a few milliseconds), but when you're dealing with O(x^3) complexity, those few milliseconds can translate to a lot of time.

    On top of that, there's a little bit of overhead using Block objects. This may or may not be a big deal depending on exactly what you have min/max X,Y,Z set to.

    What you should do instead is keep a list of key/value pairs you plan on saving to the configuration file, but keep those in ram before you try writing them to disk. The easiest way to do so is just to follow 1Rogue's advice and move...
    Code:
    File pFile = new File(path);
    FileConfiguration pConfig = YamlConfiguration.loadConfiguration(pFile);
    
    ... outside of the for loops, and move the save call to after the for loops have finished executing. You're able to do this since I believe FileConfiguration uses an in-memory map to store values until you actually tell it to save to file. If that's not the case, just make your own. Moving the other variables you're using from inside the loop to outside won't do much.

    Also, you don't need to set the "blocks" config value every time either. Set it once at the end of the loop (using "i" to figure out how many blocks were saved). The same thing applies to world.

    Also, I think you meant to save "x"+i as well. You're only saving y and z.
     
  12. Offline

    LordManegane

    FinalFred Thanks!!! Now it works mutch better, its stays lagging the game but its a lot faster.
    I really made a mistake because i put the pFile and pConfig at the for and i doesnt get that i do that.
    Also thank to all the people that reply.
     
  13. Offline

    drtshock

    I would also check to make sure that file exists before you load it as a yaml configuration. Null checks are best checks ;)
     
    sgavster likes this.
Thread Status:
Not open for further replies.

Share This Page