Export 0.2.1
[platform/framework/web/web-ui-fw.git] / libs / js / jquery-mobile-1.2.0 / node_modules / grunt / node_modules / glob-whatev / node_modules / minimatch / node_modules / lru-cache / lib / lru-cache.js
1 ;(function () { // closure for web browsers
2
3 if (typeof module === 'object' && module.exports) {
4   module.exports = LRUCache
5 } else {
6   // just set the global for non-node platforms.
7   this.LRUCache = LRUCache
8 }
9
10 function hOP (obj, key) {
11   return Object.prototype.hasOwnProperty.call(obj, key)
12 }
13
14 function naiveLength () { return 1 }
15
16 function LRUCache (options) {
17   if (!(this instanceof LRUCache)) {
18     return new LRUCache(options)
19   }
20
21   var max
22   if (typeof options === 'number') {
23     max = options
24     options = { max: max }
25   }
26   max = options.max
27
28   if (!options) options = {}
29
30   var lengthCalculator = options.length || naiveLength
31
32   if (typeof lengthCalculator !== "function") {
33     lengthCalculator = naiveLength
34   }
35   if (!max || !(typeof max === "number") || max <= 0 ) {
36     // a little bit silly.  maybe this should throw?
37     max = Infinity
38   }
39
40   var maxAge = options.maxAge || null
41
42   var dispose = options.dispose
43
44   var cache = Object.create(null) // hash of items by key
45     , lruList = Object.create(null) // list of items in order of use recency
46     , mru = 0 // most recently used
47     , length = 0 // number of items in the list
48     , itemCount = 0
49
50
51   // resize the cache when the max changes.
52   Object.defineProperty(this, "max",
53     { set : function (mL) {
54         if (!mL || !(typeof mL === "number") || mL <= 0 ) mL = Infinity
55         max = mL
56         // if it gets above double max, trim right away.
57         // otherwise, do it whenever it's convenient.
58         if (length > max) trim()
59       }
60     , get : function () { return max }
61     , enumerable : true
62     })
63
64   // resize the cache when the lengthCalculator changes.
65   Object.defineProperty(this, "lengthCalculator",
66     { set : function (lC) {
67         if (typeof lC !== "function") {
68           lengthCalculator = naiveLength
69           length = itemCount
70           for (var key in cache) {
71             cache[key].length = 1
72           }
73         } else {
74           lengthCalculator = lC
75           length = 0
76           for (var key in cache) {
77             cache[key].length = lengthCalculator(cache[key].value)
78             length += cache[key].length
79           }
80         }
81
82         if (length > max) trim()
83       }
84     , get : function () { return lengthCalculator }
85     , enumerable : true
86     })
87
88   Object.defineProperty(this, "length",
89     { get : function () { return length }
90     , enumerable : true
91     })
92
93
94   Object.defineProperty(this, "itemCount",
95     { get : function () { return itemCount }
96     , enumerable : true
97     })
98
99   this.reset = function () {
100     if (dispose) {
101       for (var k in cache) {
102         dispose(k, cache[k].value)
103       }
104     }
105     cache = {}
106     lruList = {}
107     mru = 0
108     length = 0
109     itemCount = 0
110   }
111
112   // Provided for debugging/dev purposes only. No promises whatsoever that
113   // this API stays stable.
114   this.dump = function () {
115     return cache
116   }
117
118   this.set = function (key, value) {
119     if (hOP(cache, key)) {
120       // dispose of the old one before overwriting
121       if (dispose) dispose(key, cache[key].value)
122       if (maxAge) cache[key].now = Date.now()
123       cache[key].value = value
124       this.get(key)
125       return true
126     }
127
128     var len = lengthCalculator(value)
129     var age = maxAge ? Date.now() : 0
130     var hit = new Entry(key, value, mru++, len, age)
131
132     // oversized objects fall out of cache automatically.
133     if (hit.length > max) {
134       if (dispose) dispose(key, value)
135       return false
136     }
137
138     length += hit.length
139     lruList[hit.lu] = cache[key] = hit
140     itemCount ++
141
142     if (length > max) trim()
143     return true
144   }
145
146   this.get = function (key) {
147     if (!hOP(cache, key)) return
148     var hit = cache[key]
149     if (maxAge && (Date.now() - hit.now > maxAge)) {
150       this.del(key)
151       return
152     }
153     delete lruList[hit.lu]
154     hit.lu = mru ++
155     lruList[hit.lu] = hit
156     return hit.value
157   }
158
159   this.del = function (key) {
160     if (!hOP(cache, key)) return
161     var hit = cache[key]
162     if (dispose) dispose(key, hit.value)
163     delete cache[key]
164     delete lruList[hit.lu]
165     length -= hit.length
166     itemCount --
167   }
168
169   function trim () {
170     if (length <= max) return
171     for (var k in lruList) {
172       if (length <= max) break;
173       var hit = lruList[k]
174       if (dispose) dispose(hit.key, hit.value)
175       length -= hit.length
176       delete cache[ hit.key ]
177       delete lruList[k]
178     }
179   }
180 }
181
182 // classy, since V8 prefers predictable objects.
183 function Entry (key, value, mru, len, age) {
184   this.key = key
185   this.value = value
186   this.lu = mru
187   this.length = len
188   this.now = age
189 }
190
191 })()