def classify_from_patchlist(imlist, imdict, pyparams, net, scorelayer = 'score', startlayer = 'conv1_1'):

    estlist, scorelist, gtlist = [], [], []
    transformer = Transformer(pyparams['im_mean'])
    for imname in imlist:
        
        patchlist = []
        (point_anns, height_cm) = imdict[os.path.basename(imname)]

        # Load image
        im = np.asarray(Image.open(imname))
        (im, scale) = coral_image_resize(im, pyparams['scaling_method'], pyparams['scaling_factor'], height_cm) #resize.

        # Pad the boundaries
        im = np.pad(im, ((pyparams['crop_size']*2, pyparams['crop_size']*2),(pyparams['crop_size']*2, pyparams['crop_size']*2), (0, 0)), mode='reflect')        
        
        # Extract patches
        for (row, col, label) in point_anns:
            center_org = np.asarray([row, col])
            center = np.round(pyparams['crop_size']*2 + center_org * scale).astype(np.int)
            patchlist.append(crop_and_rotate(im, center, pyparams['crop_size'], 0, tile = False))
            gtlist.append(label)

        # Classify and append
        [this_estlist, this_scorelist] = classify_imlist(patchlist, net, transformer, pyparams['batch_size'], scorelayer = scorelayer, startlayer = startlayer)
        estlist.extend(this_estlist)
        scorelist.extend(this_scorelist)
        
    return (gtlist, estlist, scorelist)
    def __call__(self):
        t1 = timer()
        self.result['data'] = []
        self.result['label'] = []

        if self._cur + self.params['imgs_per_batch'] >= len(self.imlist):
            self._cur = 0
            shuffle(self.imlist)
        
        # Grab images names from imlist
        imnames = self.imlist[self._cur : self._cur + self.params['imgs_per_batch']]

        # Figure out how many patches to grab from each image
        patches_per_image = self.chunkify(self.params['batch_size'], self.params['imgs_per_batch'])

        # Make nice output string
        output_str = [str(npatches) + ' from ' + os.path.basename(imname) + '(id ' + str(itt) + ')' for imname, npatches, itt in zip(imnames, patches_per_image, range(self._cur, self._cur + self.params['imgs_per_batch']))]
        
        # Loop over each image
        for imname, npatches in zip(imnames, patches_per_image):
            self._cur += 1

            # randomly select the rotation angle for each patch             
            angles = np.random.choice(360, size = npatches, replace = True)

            # randomly select whether to flip this particular patch.
            flips = np.round(np.random.rand(npatches))*2-1

            # get random offsets
            rand_offsets = np.round(np.random.rand(npatches, 2) * (self.params['rand_offset'] * 2)  - self.params['rand_offset'])

            # Randomly permute the patch list for this image. Sampling is done with replacement 
            # so that if we ask for more patches than is available, it still computes.
            (point_anns, height_cm) = self.imdict[os.path.basename(imname)] # read point annotations and image height in centimeters.
            point_anns = [point_anns[pp] for pp in np.random.choice(len(point_anns), size = npatches, replace = True)]

            # Load image
            im = np.asarray(Image.open(imname))
            (im, scale) = coral_image_resize(im, self.params['scaling_method'], self.params['scaling_factor'], height_cm) #resize.

            # Pad the boundaries
            crop_size = self.params['crop_size'] #for convenience, store this value locally                        
            im = np.pad(im, ((crop_size * 2, crop_size * 2),(crop_size * 2, crop_size * 2), (0, 0)), mode='reflect')        
            for ((row, col, label), angle, flip, rand_offset) in zip(point_anns, angles, flips, rand_offsets):
                center_org = np.asarray([row, col])
                center = np.round(crop_size * 2 + center_org * scale + rand_offset).astype(np.int)
                patch = self.transformer(crop_and_rotate(im, center, crop_size, angle, tile = False))
                self.result['data'].append(patch[::flip, :, :])
                self.result['label'].append(label)
def classify_from_patchlist(imlist, imdict, pyparams, workdir, scorelayer = 'score', startlayer = 'conv1_1', net_prototxt = 'testnet.prototxt', gpuid = 0, snapshot_prefix = 'snapshot', save = False):

    # Preliminaries    
    caffemodel = find_latest_caffemodel(workdir, snapshot_prefix = snapshot_prefix)
    net = load_model(workdir, caffemodel, gpuid = gpuid, net_prototxt = net_prototxt)
    transformer = Transformer(pyparams['im_mean'])
    estlist, scorelist, gtlist = [], [], []
    
    print "classifying {} images in {} using {}".format(len(imlist), workdir, caffemodel)
    for imname in tqdm(imlist):
        
        patchlist = []
        (point_anns, height_cm) = imdict[os.path.basename(imname)]

        # Load image
        im = np.asarray(Image.open(imname))
        (im, scale) = coral_image_resize(im, pyparams['scaling_method'], pyparams['scaling_factor'], height_cm) #resize.

        # Pad the boundaries                        
        im = np.pad(im, ((pyparams['crop_size']*2, pyparams['crop_size']*2),(pyparams['crop_size']*2, pyparams['crop_size']*2), (0, 0)), mode='reflect')        
        
        # Extract patches
        for (row, col, label) in point_anns:
            center_org = np.asarray([row, col])
            center = np.round(pyparams['crop_size']*2 + center_org * scale).astype(np.int)
            patchlist.append(crop_and_rotate(im, center, pyparams['crop_size'], 0, tile = False))
            gtlist.append(label)

        # Classify and append
        [this_estlist, this_scorelist] = classify_imlist(patchlist, net, transformer, pyparams['batch_size'], scorelayer = scorelayer, startlayer = startlayer)
        estlist.extend(this_estlist)
        scorelist.extend(this_scorelist)
        
    if (save):
        pickle.dump((gtlist, estlist, scorelist), open(os.path.join(workdir, 'predictions_using_' + caffemodel +  '.p'), 'wb'))
    return [gtlist, estlist, scorelist]
    def __call__(self):
        t1 = timer()
        self.result['data'] = []
        self.result['label'] = []

        if self._cur + self.params['imgs_per_batch'] >= len(self.imlist):
            self._cur = 0
            shuffle(self.imlist)

        # Grab images names from imlist
        imnames = self.imlist[self._cur:self._cur +
                              self.params['imgs_per_batch']]

        # Figure out how many patches to grab from each image
        patches_per_image = self.chunkify(self.params['batch_size'],
                                          self.params['imgs_per_batch'])

        # Make nice output string
        output_str = [
            str(npatches) + ' from ' + os.path.basename(imname) + '(id ' +
            str(itt) + ')' for imname, npatches, itt in zip(
                imnames, patches_per_image,
                range(self._cur, self._cur + self.params['imgs_per_batch']))
        ]

        # Loop over each image
        for imname, npatches in zip(imnames, patches_per_image):
            self._cur += 1

            # randomly select the rotation angle for each patch
            angles = np.random.choice(360, size=npatches, replace=True)

            # randomly select whether to flip this particular patch.
            flips = np.round(np.random.rand(npatches)) * 2 - 1

            # get random offsets
            rand_offsets = np.round(
                np.random.rand(npatches, 2) *
                (self.params['rand_offset'] * 2) - self.params['rand_offset'])

            # Randomly permute the patch list for this image. Sampling is done with replacement
            # so that if we ask for more patches than is available, it still computes.
            (point_anns, height_cm) = self.imdict[os.path.basename(
                imname
            )]  # read point annotations and image height in centimeters.
            point_anns = [
                point_anns[pp] for pp in np.random.choice(
                    len(point_anns), size=npatches, replace=True)
            ]

            # Load image
            im = np.asarray(Image.open(imname))
            (im, scale) = coral_image_resize(im, self.params['scaling_method'],
                                             self.params['scaling_factor'],
                                             height_cm)  #resize.

            # Pad the boundaries
            crop_size = self.params[
                'crop_size']  #for convenience, store this value locally
            im = np.pad(im, ((crop_size * 2, crop_size * 2),
                             (crop_size * 2, crop_size * 2), (0, 0)),
                        mode='reflect')
            for ((row, col, label), angle, flip,
                 rand_offset) in zip(point_anns, angles, flips, rand_offsets):
                center_org = np.asarray([row, col])
                center = np.round(crop_size * 2 + center_org * scale +
                                  rand_offset).astype(np.int)
                patch = self.transformer(
                    crop_and_rotate(im, center, crop_size, angle, tile=False))
                self.result['data'].append(patch[::flip, :, :])
                self.result['label'].append(label)