function data = read_boxes(filename)
% data = read_boxes(filename)
%
% Reads a file for ImageNet ids and bounding boxes
% 'data' is a struct variable with two fields: 
% 'imid' is an 1xN cell array with N ImageNet image identifiers.
% 'box' is an Nx5 double array where each line provides a bounding box for the corresponding image.
%
% An ImageNet id looks like this: 'n01322604_10013'.
% This means it is image '10013' from the ImageNet synset 'n01322604'.
% You can browse the synset with:
%    http://www.image-net.org/synset?wnid=n01322604
% You can get the url of a specific image with:
%    wget -O /dev/stdout http://www.image-net.org/api/text/imagenet.synset.geturls.getmapping?wnid=n01322604 2> /dev/null | grep n01322604_10013
%
% The 5 columns of 'box' are the following:
% - the left border of the bounding box (xmin)
% - the top border of the bounding box (ymin)
% - the right border of the bounding box (xmax)
% - the bottom border of the bounding box (ymax)
% - the score of the bounding box (ie, the score of our method for automatic boxes, 1 for all GT boxes)

headerclass = 'int';
imhashclass = 'uint64';
posclass = 'uint16';
scoreclass = 'double';

fid = fopen(filename,'rb');
n = fread(fid,1,headerclass);
imid = cell(1,n);
boxes = zeros(n,5);
tic;
for i=1:n,
  hash = uint64(fread(fid,1,imhashclass));
  imid{i} = uint2imid(hash);
  box(i,1:4) = double(uint16(fread(fid,4,posclass)));
  box(i,5) = double(fread(fid,1,scoreclass));
  if toc>5,
    fprintf('%d/%d\n',i,n);
    tic;
  end
end
fclose(fid);
data.imid = imid;
data.box = box;
end

function imid = uint2imid(hash)
if isa(hash,'uint64'), % hash is an image id
    imid = dec2base(bitshift(hash,-32),11);
    imid(imid=='A') = '-';
    imid = [ '_' imid ];
    hash = bitshift(bitshift(hash,32),-32);
elseif isa(hash,'uint32'),
    imid = '';
else
    error('invalid hash');
end
imid = sprintf('n%08d%s',hash,imid);
end

