@not_in_run<EOL><INDENT>@kwargs_api_change('<STR_LIT>', '<STR_LIT>')<EOL>@kwargs_api_change('<STR_LIT>', '<STR_LIT>')<EOL>@kwargs_api_change('<STR_LIT>')<EOL>@kwargs_api_change('<STR_LIT>')<EOL>def f_merge(self, other_trajectory, trial_parameter=None, remove_duplicates=False,<EOL>ignore_data=(),<EOL>backup=True,<EOL>move_data=False,<EOL>delete_other_trajectory=False,<EOL>keep_info=True,<EOL>keep_other_trajectory_info=True,<EOL>merge_config=True,<EOL>consecutive_merge=False,<EOL>slow_merge=False):<DEDENT>
if consecutive_merge and trial_parameter is not None:<EOL><INDENT>self._logger.warning('<STR_LIT>'<EOL>'<STR_LIT>')<EOL><DEDENT>if consecutive_merge and backup:<EOL><INDENT>self._logger.warning('<STR_LIT>'<EOL>'<STR_LIT>')<EOL><DEDENT>timestamp = time.time()<EOL>original_ignore_data = set(ignore_data)<EOL>ignore_data = original_ignore_data.copy()<EOL>old_len = len(self)<EOL>self._check_if_both_have_same_parameters(other_trajectory, ignore_data, consecutive_merge)<EOL>self._make_reversed_wildcards(old_length=old_len)<EOL>other_trajectory._make_reversed_wildcards()<EOL>if backup:<EOL><INDENT>other_trajectory.f_backup()<EOL>self.f_backup()<EOL><DEDENT>self._logger.info('<STR_LIT>')<EOL>used_runs, changed_parameters = self._merge_parameters(<EOL>other_trajectory,<EOL>remove_duplicates,<EOL>trial_parameter,<EOL>ignore_data)<EOL>ignore_data.update(set(changed_parameters))<EOL>if len(used_runs) == <NUM_LIT:0>:<EOL><INDENT>raise ValueError('<STR_LIT>'<EOL>'<STR_LIT>')<EOL><DEDENT>rename_dict = {}<EOL>self._logger.info('<STR_LIT>')<EOL>allowed_translations = set([translation for translation, pair in<EOL>other_trajectory._reversed_wildcards.items() if<EOL>any(x in used_runs for x in pair[<NUM_LIT:0>])])<EOL>self._merge_single_runs(other_trajectory, used_runs)<EOL>self._logger.info('<STR_LIT>')<EOL>self._merge_derived_parameters(other_trajectory=other_trajectory,<EOL>used_runs=used_runs,<EOL>rename_dict=rename_dict,<EOL>allowed_translations=allowed_translations,<EOL>ignore_data=ignore_data)<EOL>self._merge_results(other_trajectory=other_trajectory,<EOL>used_runs=used_runs,<EOL>rename_dict=rename_dict,<EOL>allowed_translations=allowed_translations,<EOL>ignore_data=ignore_data)<EOL>self._logger.info('<STR_LIT>')<EOL>self._logger.info('<STR_LIT>')<EOL>self._storage_service.store(pypetconstants.PREPARE_MERGE, self,<EOL>trajectory_name=self.v_name,<EOL>changed_parameters=changed_parameters,<EOL>old_length=old_len)<EOL>if not slow_merge:<EOL><INDENT>try:<EOL><INDENT>try:<EOL><INDENT>other_filename = other_trajectory.v_storage_service.filename<EOL><DEDENT>except AttributeError:<EOL><INDENT>self._logger.warning('<STR_LIT>'<EOL>'<STR_LIT>')<EOL>other_filename = None<EOL><DEDENT>self._storage_service.store(pypetconstants.MERGE, '<STR_LIT>', trajectory_name=self.v_name,<EOL>other_trajectory_name=other_trajectory.v_name,<EOL>rename_dict=rename_dict, move_nodes=move_data,<EOL>delete_trajectory=delete_other_trajectory,<EOL>other_filename=other_filename)<EOL><DEDENT>except pex.NoSuchServiceError as exc:<EOL><INDENT>self._logger.exception('<STR_LIT>'<EOL>'<STR_LIT>'<EOL>'<STR_LIT>'<EOL>'<STR_LIT>'<EOL>'<STR_LIT>')<EOL>slow_merge = True<EOL><DEDENT>except ValueError as exc:<EOL><INDENT>self._logger.exception('<STR_LIT>'<EOL>'<STR_LIT>'<EOL>'<STR_LIT>'<EOL>'<STR_LIT>'<EOL>'<STR_LIT>')<EOL>slow_merge = True<EOL><DEDENT><DEDENT>if slow_merge:<EOL><INDENT>self._merge_slowly(other_trajectory, rename_dict)<EOL><DEDENT>if merge_config:<EOL><INDENT>self._merge_config(other_trajectory)<EOL><DEDENT>self._merge_links(other_trajectory=other_trajectory,<EOL>used_runs=used_runs,<EOL>allowed_translations=allowed_translations,<EOL>ignore_data=original_ignore_data)<EOL>self._logger.info('<STR_LIT>')<EOL>formatted_time = datetime.datetime.fromtimestamp(timestamp).strftime('<STR_LIT>')<EOL>hexsha = hashlib.sha1((self.v_name +<EOL>str(self.v_timestamp) +<EOL>other_trajectory.v_name +<EOL>str(other_trajectory.v_timestamp) +<EOL>VERSION).encode('<STR_LIT:utf-8>')).hexdigest()<EOL>short_hexsha = hexsha[<NUM_LIT:0>:<NUM_LIT:7>]<EOL>if keep_info:<EOL><INDENT>merge_name = '<STR_LIT>' % (short_hexsha, formatted_time)<EOL>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, len(used_runs),<EOL>comment='<STR_LIT>')<EOL>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, timestamp,<EOL>comment='<STR_LIT>')<EOL>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, hexsha,<EOL>comment='<STR_LIT>')<EOL>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, remove_duplicates,<EOL>comment='<STR_LIT>')<EOL>if original_ignore_data:<EOL><INDENT>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, tuple(original_ignore_data),<EOL>comment='<STR_LIT>')<EOL><DEDENT>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, len(self),<EOL>comment='<STR_LIT>')<EOL>self.config.merge.v_comment = '<STR_LIT>'<EOL>if self.v_version != VERSION:<EOL><INDENT>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, self.v_version,<EOL>comment='<STR_LIT>'<EOL>'<STR_LIT>')<EOL><DEDENT>if trial_parameter is not None:<EOL><INDENT>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, len(other_trajectory),<EOL>comment='<STR_LIT>')<EOL><DEDENT>if keep_other_trajectory_info:<EOL><INDENT>if other_trajectory.v_version != self.v_version:<EOL><INDENT>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, other_trajectory.v_version,<EOL>comment='<STR_LIT>'<EOL>'<STR_LIT>'<EOL>'<STR_LIT>')<EOL><DEDENT>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, other_trajectory.v_name,<EOL>comment='<STR_LIT>')<EOL>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, other_trajectory.v_timestamp,<EOL>comment='<STR_LIT>'<EOL>'<STR_LIT>')<EOL>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, len(other_trajectory),<EOL>comment='<STR_LIT>')<EOL>if other_trajectory.v_comment:<EOL><INDENT>config_name = '<STR_LIT>' % merge_name<EOL>self.f_add_config(config_name, other_trajectory.v_comment,<EOL>comment='<STR_LIT>')<EOL><DEDENT><DEDENT><DEDENT>if not consecutive_merge:<EOL><INDENT>self._logger.info('<STR_LIT>')<EOL>self.f_store(store_data=pypetconstants.STORE_DATA)<EOL>self._reversed_wildcards = {}<EOL><DEDENT>other_trajectory._reversed_wildcards = {}<EOL>self._logger.info('<STR_LIT>')<EOL>
Merges another trajectory into the current trajectory.

        Both trajectories must live in the same space. This means both need to have the same
        parameters with similar types of values.

        Note that links are also merged. There are exceptions: Links found under
        a generic run group called `run_ALL` or links linking to a node under such a
        group are NOT merged and simply skipped, because there is no straightforward
        way to resolve the link.

        :param other_trajectory: Other trajectory instance to merge into the current one.

        :param trial_parameter:

            If you have a particular parameter that specifies only the trial
            number, i.e. an integer parameter running form 0 to T1 and
            0 to T2, the parameter is modified such that after merging it will
            cover the range 0 to T1+T2+1. T1 is the number of individual trials in the current
            trajectory and T2 number of trials in the other trajectory.

        :param remove_duplicates:

            Whether you want to remove duplicate parameter points.
            Requires N1 * N2 (quadratic complexity in single runs).
            A ValueError is raised if no runs would be merged.

        :param ignore_data:

            List of full names of data that should be ignored and not merged.

        :param backup:

            If ``True``, backs up both trajectories into files chosen automatically
            by the storage services. If you want to customize your backup use
            the `f_backup` function instead.

        :param move_data:

           Tells the storage service to move data from one trajectory to the other
           instead of copying it.

           If you use the HDF5 storage service and both trajectories are
           stored in the same file, merging is performed fast directly within
           the file. You can choose if you want to copy nodes ('move_nodes=False`)
           from the other trajectory to the current one, or if you want to move them.
           Accordingly, the stored data is no longer accessible in the other trajectory.

        :param delete_other_trajectory:

            If you want to delete the other trajectory after merging.

        :param keep_info:

            If `True`, information about the merge is added to the trajectory `config` tree under
            `config.merge`.

        :param merge_config:

            Whether or not to merge all config parameters under `.config.git`,
            `.config.environment`, and `.config.merge` of the other trajectory
            into the current one.

        :param keep_other_trajectory_info:

            Whether to keep information like length, name, etc. of the other trajectory
            in case you want to keep all the information. Setting of `keep_other_trajectory_info`
            is irrelevant in case `keep_info=False`.

        :param consecutive_merge:
            Can be set to `True` if you are about to merge several trajectories into the current
            one within a loop to avoid quadratic complexity.
            But remember to store your trajectory manually after
            all merges. Also make sure that all parameters and derived parameters are available
            in your current trajectory and load them before the consecutive merging.
            Also avoid specifying a `trial_parameter` and set `backup=False`
            to avoid quadratic complexity in case of consecutive merges.

        :param slow_merge:
            Enforces a slow merging. This means all data is loaded one after the other to
            memory and stored to disk. Otherwise it is tried to directly copy the data
            from one file into another without explicitly loading the data.

        If you cannot directly merge trajectories within one HDF5 file, a slow merging process
        is used. Results are loaded, stored, and emptied again one after the other. Might take
        some time!

        Annotations of parameters and derived parameters under `.derived_parameters.trajectory`
        are NOT merged. If you wish to extract the annotations of these parameters you have to
        do that manually before merging. Note that annotations of results and derived parameters
        of single runs are copied, so you don't have to worry about these.