summaryrefslogtreecommitdiffstats
path: root/logo/src/xlogo/storage/cache/ObjectCache.java
blob: 0fc6a30f76dcae785a6b11de19a0553d1ecc89a2 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
package xlogo.storage.cache;

import java.io.File;
import java.util.HashMap;

import xlogo.interfaces.Observable;
import xlogo.storage.StorableObject;

/**
 * Cache {@link StorableObject} based on {@link StorableObject#getFilePath()}
 * @author Marko
 *
 */
public class ObjectCache {
	
	/*
	 * Singleton
	 */
	
	private static ObjectCache instance;
	
	public static final ObjectCache getInstance(){
		if(instance == null){
			instance = new ObjectCache();
		}
		return instance;
	}
	
	/*
	 * Cache fields
	 */
	
	/**
	 * Class of T -> Map({@link StorableObject#getFilePath()} -> {@link StorableObject} of T)
	 */
	private HashMap<Class<?>,HashMap<File,StorableObject<?,?>>> cache;
	
	private ObjectCache(){
		cache = new HashMap<Class<?>, HashMap<File,StorableObject<?,?>>>();
	}

	/** 
	 * Cache {@link StorableObject} based on {@link StorableObject#getFilePath()}
	 * @param storable
	 */
	public <T extends Observable<?>> void cache(StorableObject<T,?> storable){
		if (storable == null || storable.get() == null){
			// TODO log warning
			return;
		}
		Class<?> c = storable.get().getClass();
		HashMap<File, StorableObject<?,?>> classCache = cache.get(c);
		if (classCache == null){
			classCache = new HashMap<File, StorableObject<?, ?>>();
			cache.put(c, classCache);
		}
		classCache.put(storable.getFilePath(), storable);
	}
	
	/**
	 * 
	 * @param file
	 * @param c
	 * @return
	 */
	@SuppressWarnings("unchecked") // implementation of cache guarantees that the cast succeeds
	public <T extends Observable<E>,E extends Enum<E>> StorableObject<T, E> get(File file, Class<T> c){
		HashMap<File, StorableObject<?, ?>> classCache = cache.get(c);
		if (classCache == null){
			return null;
		}
		return (StorableObject<T, E>) classCache.get(file);
	}
	
	public <T extends Observable<?>> void remove(StorableObject<T,?> storable){
		if (storable == null || storable.get() == null){
			return;
		}
		Class<?> c = storable.get().getClass();
		remove(storable.getFilePath(), c);
	}
	
	public void remove(File file, Class<?> c){
		HashMap<File, StorableObject<?,?>> classCache = cache.get(c);
		if (classCache == null){
			return;
		}
		classCache.remove(file);
	}
	
}