Tweak the last access extent cache to provide better caching

This commit is contained in:
Matthew Miller 2018-12-29 19:21:33 +10:00
parent 2f8bdccf65
commit 871541d8c0
2 changed files with 40 additions and 10 deletions

View File

@ -92,9 +92,8 @@ public class ForgetfulExtentBuffer extends AbstractDelegateExtent implements Pat
max = max.getMaximum(location); max = max.getMaximum(location);
} }
BlockVector3 blockVector = location; if (mask.test(location)) {
if (mask.test(blockVector)) { buffer.put(location, block.toBaseBlock());
buffer.put(blockVector, block.toBaseBlock());
return true; return true;
} else { } else {
return getExtent().setBlock(location, block); return getExtent().setBlock(location, block);

View File

@ -19,10 +19,13 @@
package com.sk89q.worldedit.extent.cache; package com.sk89q.worldedit.extent.cache;
import com.sk89q.worldedit.WorldEditException;
import com.sk89q.worldedit.extent.AbstractDelegateExtent; import com.sk89q.worldedit.extent.AbstractDelegateExtent;
import com.sk89q.worldedit.extent.Extent; import com.sk89q.worldedit.extent.Extent;
import com.sk89q.worldedit.math.BlockVector3; import com.sk89q.worldedit.math.BlockVector3;
import com.sk89q.worldedit.world.block.BaseBlock;
import com.sk89q.worldedit.world.block.BlockState; import com.sk89q.worldedit.world.block.BlockState;
import com.sk89q.worldedit.world.block.BlockStateHolder;
/** /**
* Returns the same cached {@link BlockState} for repeated calls to * Returns the same cached {@link BlockState} for repeated calls to
@ -30,7 +33,8 @@ import com.sk89q.worldedit.world.block.BlockState;
*/ */
public class LastAccessExtentCache extends AbstractDelegateExtent { public class LastAccessExtentCache extends AbstractDelegateExtent {
private CachedBlock lastBlock; private CachedBlock<BlockState> lastBlock;
private CachedBlock<BaseBlock> lastFullBlock;
/** /**
* Create a new instance. * Create a new instance.
@ -43,21 +47,48 @@ public class LastAccessExtentCache extends AbstractDelegateExtent {
@Override @Override
public BlockState getBlock(BlockVector3 position) { public BlockState getBlock(BlockVector3 position) {
CachedBlock lastBlock = this.lastBlock; CachedBlock<BlockState> lastBlock = this.lastBlock;
if (lastBlock != null && lastBlock.position.equals(position)) { if (lastBlock != null && lastBlock.position.equals(position)) {
return lastBlock.block; return lastBlock.block;
} else { } else {
BlockState block = super.getBlock(position); BlockState block = super.getBlock(position);
this.lastBlock = new CachedBlock(position, block); this.lastBlock = new CachedBlock<>(position, block);
return block; return block;
} }
} }
private static class CachedBlock { @Override
private final BlockVector3 position; public BaseBlock getFullBlock(BlockVector3 position) {
private final BlockState block; CachedBlock<BaseBlock> lastFullBlock = this.lastFullBlock;
if (lastFullBlock != null && lastFullBlock.position.equals(position)) {
return lastFullBlock.block;
} else {
BaseBlock block = super.getFullBlock(position);
this.lastFullBlock = new CachedBlock<>(position, block);
return block;
}
}
private CachedBlock(BlockVector3 position, BlockState block) { @Override
public <T extends BlockStateHolder<T>> boolean setBlock(BlockVector3 location, T block) throws WorldEditException {
if (super.setBlock(location, block)) {
if (lastFullBlock != null && lastFullBlock.position.equals(location)) {
this.lastFullBlock = new CachedBlock<>(location, block.toBaseBlock());
}
if (lastBlock != null && lastBlock.position.equals(location)) {
this.lastBlock = new CachedBlock<>(location, block.toImmutableState());
}
return true;
}
return false;
}
private static class CachedBlock<B extends BlockStateHolder<B>> {
private final BlockVector3 position;
private final B block;
private CachedBlock(BlockVector3 position, B block) {
this.position = position; this.position = position;
this.block = block; this.block = block;
} }