Esempio n. 1
0
 def __nolock_update(self, done_file, inprogress_file):
     done_file.seek(0, os.SEEK_END)
     new_done_filepos = done_file.tell()
     if new_done_filepos >= self.__done_filepos:
         if new_done_filepos > self.__done_filepos:
             done_file.seek(self.__done_filepos, os.SEEK_SET)
             new_done = list()
             while True:
                 try:
                     new_done.append(pickle.load(done_file))
                     self.__done_filepos = done_file.tell()
                 except:
                     done_file.truncate(self.__done_filepos)
                     break
             self.__done.update(new_done)
             self.__remaining.difference_update(new_done)
             self.__filtered_done.update(
                 set(new_done).intersection(self.__sweeps))
         inprogress_file.seek(0, os.SEEK_SET)
         try:
             self.__inprogress = pickle.load(inprogress_file)
         except:
             inprogress_file.truncate(0)
             self.__inprogress.clear()
         self.__remaining.difference_update(self.__inprogress)
         self.__filtered_inprogress.intersection_update(self.__inprogress)
     else:
         self.__nolock_full_update(done_file, inprogress_file)
Esempio n. 2
0
def igeom(range_min, range_max, num_steps):
    """Return an integer geometric progression from range_min to range_max with num_steps"""
    if num_steps == 0: return []
    if num_steps == 1: return [int(range_min)]
    return sorted(
        set([int(range_min)] +
            [int(round(x)) for x in geom(range_min, range_max, num_steps)] +
            [int(range_max)]))
Esempio n. 3
0
 def cancel_batch(self, combinations):
     """cancel processing of the given combination(s), but don't mark it/them as skipped, they comes back in the *todo* queue."""
     with self.__lock:
         with _openlock(os.path.join(self.__persistence_dir,
                                     "done")) as done_file:
             with _openlock(
                     os.path.join(self.__persistence_dir,
                                  "inprogress")) as inprogress_file:
                 self.__nolock_update(done_file, inprogress_file)
                 filtered_combinations = set(combinations)
                 filtered_combinations.intersection_update(self.__sweeps)
                 self.__remaining.update(filtered_combinations)
                 self.__inprogress.difference_update(combinations)
                 self.__filtered_inprogress.difference_update(combinations)
                 inprogress_file.truncate(0)
                 pickle.dump(self.__inprogress, inprogress_file)
         logger.trace("%s combinations cancelled: %s", self.__name,
                      combinations)
         logger.trace(self)
Esempio n. 4
0
 def skip_batch(self, combinations):
     """mark the given element(s) *skipped*"""
     with self.__lock:
         with _openlock(os.path.join(self.__persistence_dir,
                                     "done")) as done_file:
             with _openlock(
                     os.path.join(self.__persistence_dir,
                                  "inprogress")) as inprogress_file:
                 self.__nolock_update(done_file, inprogress_file)
                 self.__skipped.update(combinations)
                 filtered_combinations = set(combinations)
                 filtered_combinations.intersection_update(self.__sweeps)
                 self.__filtered_skipped.update(filtered_combinations)
                 self.__inprogress.difference_update(combinations)
                 self.__filtered_inprogress.difference_update(combinations)
                 inprogress_file.truncate(0)
                 pickle.dump(self.__inprogress, inprogress_file)
         logger.trace("%s combinations skipped: %s", self.__name,
                      combinations)
         logger.trace(self)
Esempio n. 5
0
 def done_batch(self, combinations):
     """mark the given element(s) *done*"""
     with self.__lock:
         with _openlock(os.path.join(self.__persistence_dir,
                                     "done")) as done_file:
             with _openlock(
                     os.path.join(self.__persistence_dir,
                                  "inprogress")) as inprogress_file:
                 self.__nolock_update(done_file, inprogress_file)
                 self.__remaining.difference_update(combinations)
                 self.__inprogress.difference_update(combinations)
                 self.__filtered_inprogress.difference_update(combinations)
                 self.__done.update(combinations)
                 filtered_combinations = set(combinations)
                 filtered_combinations.intersection_update(self.__sweeps)
                 self.__filtered_done.update(filtered_combinations)
                 done_file.seek(0, os.SEEK_END)
                 for combination in combinations:
                     pickle.dump(combination, done_file)
                 inprogress_file.truncate(0)
                 pickle.dump(self.__inprogress, inprogress_file)
         logger.trace("%s combinations done: %s", self.__name, combinations)
         logger.trace(self)
Esempio n. 6
0
 def __nolock_full_update(self, done_file, inprogress_file):
     self.__done.clear()
     self.__done_filepos = 0
     done_file.seek(0, os.SEEK_SET)
     while True:
         try:
             self.__done.add(pickle.load(done_file))
             self.__done_filepos = done_file.tell()
         except:
             done_file.truncate(self.__done_filepos)
             break
     inprogress_file.seek(0, os.SEEK_SET)
     try:
         self.__inprogress = pickle.load(inprogress_file)
     except:
         inprogress_file.truncate(0)
         self.__inprogress.clear()
     self.__remaining = set(self.__sweeps).difference(
         self.__done, self.__skipped, self.__inprogress)
     self.__filtered_done = self.__done.intersection(self.__sweeps)
     self.__filtered_inprogress = self.__inprogress.intersection(
         self.__sweeps)
     self.__filtered_skipped = self.__skipped.intersection(self.__sweeps)
Esempio n. 7
0
    def set_sweeps(self, sweeps=None, save_sweeps=False):
        """Change the list of what to iterate on.

        :param sweeps: iterable

        :param save_sweeps: boolean. default False. If True, the
          sweeps are written to disk.
        """
        with self.__lock:
            if sweeps:
                self.__sweeps = set(sweeps)
                if save_sweeps:
                    with _openlock(
                            os.path.join(self.__persistence_dir,
                                         "sweeps")) as sweeps_file:
                        sweeps_file.truncate(0)
                        pickle.dump(self.__sweeps, sweeps_file)
            else:
                with _openlock(os.path.join(self.__persistence_dir,
                                            "sweeps")) as sweeps_file:
                    sweeps_file.seek(0, os.SEEK_SET)
                    self.__sweeps = pickle.load(sweeps_file)
            self.full_update()
Esempio n. 8
0
    def __init__(self,
                 persistence_dir,
                 sweeps=None,
                 save_sweeps=False,
                 name=None):
        """
        :param persistence_dir: path to persistence directory. In this
          directory will be created to python pickle files: ``done``
          and ``inprogress`` This files can be erased if needed.

        :param sweeps: An iterable, what to iterate on. If None
          (default), try to load it from ``persistence_dir``

        :param save_sweeps: boolean. default False. If True, the
          sweeps are written to disk during initialization (this may
          take some time but occurs only once)

        :param name: a convenient name to identify an instance in
          logs. If None, compute one from persistence_dir.
        """
        self.__lock = threading.RLock()
        self.__persistence_dir = persistence_dir
        try:
            os.makedirs(self.__persistence_dir)
        except os.error:
            pass
        self.__name = name
        if not self.__name:
            self.__name = os.path.basename(self.__persistence_dir)

        self.__done = set()
        self.__inprogress = set()
        self.__skipped = set()

        self.__filtered_done = set()
        self.__filtered_inprogress = set()
        self.__filtered_skipped = set()
        # __filtered_done, __filtered_inprogress, __filtered_skipped
        # are the intersections of __sweeps and __done, __inprogress,
        # __skipped. They exist because:
        #
        # - client may call set_sweeps with different sweeps, still we
        #   want to remember the complete list of __done,
        #   __inprogress, __skipped
        #
        # - different ParamSweeper instances may share the same
        #   storage though having different individual
        #   __sweeps. __inprogress and __done on storage will be the
        #   union of all inprogress and done, so the ParamSweeper must
        #   be prepared to deal correctly with __inprogress and __done
        #   containing elements not in *its* __sweeps (and it must not
        #   discard them)
        #
        # - on the other hand, when displaying with __str__(),
        #   stats(), or when retrieving with get_done(),
        #   get_inprogress(), get_skipped(), client expects to get
        #   only lists of done, inprogress, skipped relative to the
        #   current __sweeps.
        #
        # - we could filter (do the intersection with __sweeps) only
        #   when displaying or returning the lists, but it's a costly
        #   operation to do the full intersection, whereas doing it
        #   incrementaly is fast.

        self.__remaining = set()
        self.__done_filepos = None

        self.set_sweeps(sweeps, save_sweeps)