Utilizziamo un caricamento Google Guava LoadingCache per bitmap in un'applicazione Android. Nell'applicazione sto eseguendo un Thread di disegno, che dipinge le bitmap nella cache su un Canvas. Se una bitmap specifica non è nella cache, non viene disegnata in modo che nessun caricamento bloccherà mai il Thread del disegno.Scarse prestazioni con Guava Cache su Android
Tuttavia, il dipinto genera una balbuzie visiva e la velocità dei fotogrammi al secondo non è quella che vorremmo. L'ho inchiodato al metodo getIfPresent()
della cache. Questo da solo occupa oltre il 20% del tempo totale della CPU delle applicazioni. In getIfPresent()
LocalCache$Segment.get()
riprende 80% del tempo:
tenga presente, questa è solo una ricerca di un già presenti bitmap. Non ci sarà mai un carico in get()
. Ho pensato che ci sarebbe stato un overhead contabile in get()
per la coda LRU che decide quale sfratto si verifica se il segmento è pieno. Ma questo è almeno un ordine di grandezza più lento di quello che mi darebbe un in LRU-LinkedHashmap.get()
.
Utilizziamo una cache per ottenere ricerche veloci se un elemento è nella cache, se la ricerca è lenta, non è necessario memorizzarla nella cache. Ho anche provato getAllPresent(a)
e asMap()
ma offre prestazioni uguali.
versione Library è: guava-11.0.1.jar
LoadingCache è definito come segue:
LoadingCache<TileKey, Bitmap> tiles = CacheBuilder.newBuilder().maximumSize(100).build(new CacheLoader<TileKey,Bitmap>() {
@Override
public Bitmap load(TileKey tileKey) {
System.out.println("Loading in " + Thread.currentThread().getName() + " "
+ tileKey.x + "-" + tileKey.y);
final File[][] tileFiles = surfaceState.mapFile.getBuilding()
.getFloors().get(tileKey.floorid)
.getBackground(tileKey.zoomid).getTileFiles();
String tilePath = tileFiles[tileKey.y][tileKey.x].getAbsolutePath();
Options options = new BitmapFactory.Options();
options.inPreferredConfig = Bitmap.Config.RGB_565;
return BitmapFactory.decodeFile(tilePath, options);
}
});
Le mie domande sono:
- faccio a utilizzarlo sbagliato?
- È un'implementazione non utilizzabile per Android?
- Mi manca un'opzione di configurazione?
- Si tratta di un problema noto con la cache su cui si sta lavorando?
Aggiornamento:
Dopo circa 100 cornici dipinte le CacheStats sono:
I/System.out(6989): CacheStats{hitCount=11992, missCount=97,
loadSuccessCount=77, loadExceptionCount=0, totalLoadTime=1402984624, evictionCount=0}
Dopo che missCount rimane fondamentalmente lo stesso di incrementi HitCount. In questo caso la cache è abbastanza grande perché i carichi si verifichino scarsamente, ma getIfPresent è lento.
Si prega di fare non in grassetto ogni altra frase; era difficile da leggere, quindi ho inviato una modifica per eliminarla. – simchona
Grazie, simchona per averlo modificato per renderlo più leggibile. – user643011
Potresti pubblicare i risultati di 'tiles.cacheStats()'? –