File size: 1,461 Bytes
d0e7c02
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
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
"""Datasets. Parsed examples are cached on disk (JPEG + index.json) under SLOTREAD_CACHE, because
streaming and filtering the sources is slow (AGUVIS: up to hours) and every arm trains on the same
examples."""

import json, os, resource

from PIL import Image

CACHE = os.path.expanduser(os.environ.get("SLOTREAD_CACHE", "~/.cache/slotread"))

# cached examples are opened lazily (PIL holds one descriptor each); tens of thousands of them need a
# higher descriptor limit than the default 1024
_soft, _hard = resource.getrlimit(resource.RLIMIT_NOFILE)
resource.setrlimit(resource.RLIMIT_NOFILE, (max(_soft, min(65536, _hard)), _hard))


def load_cache(name):
    path = os.path.join(CACHE, name)
    if not os.path.exists(f"{path}/index.json"):
        return None
    out = []
    for r in json.load(open(f"{path}/index.json")):
        r = dict(r)
        r["image"] = Image.open(f"{path}/{r.pop('file')}")
        out.append(r)
    print(f"  cache: {len(out)} examples from {path}", flush=True)
    return out


def save_cache(name, rows):
    path = os.path.join(CACHE, name)
    os.makedirs(path, exist_ok=True)
    idx = []
    for i, r in enumerate(rows):
        f = f"{i:05d}.jpg"
        r["image"].convert("RGB").save(f"{path}/{f}", "JPEG", quality=88)
        idx.append({k: v for k, v in r.items() if k != "image"} | {"file": f})
    json.dump(idx, open(f"{path}/index.json", "w"))
    print(f"  cached {len(rows)} examples to {path}", flush=True)