예제 #1
0
def set_cp2k_param(settings: Settings, param_dict: dict) -> None:
    """Placeholder."""
    for block_name, block in param_dict.items():
        # Create a to-be formatted string with user-specified units
        unit = f'[{block.unit}]' + ' {}' if 'unit' in block else '{}'

        # Get the to-be update list of settings
        s = settings.get_nested(block['keys'])
        if not isinstance(s, list):
            _s = settings.get_nested(block['keys'][:-1])
            s = _s[block['keys'][-1]] = []

        for k, v in block.items():
            if k in ('keys', 'unit'):  # Skip
                continue

            value = unit.format(v)
            atom = 'atoms' if len(k.split()) > 1 else 'atom'
            atom_list = [i[atom] for i in s]

            try:  # Intersecting set
                idx = atom_list.index(k)
                s[idx].update({block_name: value})
            except ValueError:  # Disjoint set
                new_block = Settings({atom: k, block_name: value})
                s.append(new_block)
예제 #2
0
    def _overlay_cp2k_settings(self, cp2k_settings: Settings,
                               name: str, columns: MutableSequence[int],
                               key_path: Sequence[str], key: Iterable[str],
                               unit: Iterable[str], default_unit: Iterable[Optional[str]],
                               post_process: Iterable[Optional[PostProcess]]) -> None:
        """Helper function for :meth:`PRMContainer.overlay_cp2k_settings`."""
        # Extract the appropiate dict or sequence of dicts
        try:
            prm_iter = Settings.get_nested(cp2k_settings, key_path)
        except KeyError:
            return
        else:
            prm_iter = (prm_iter,) if isinstance(prm_iter, Mapping) else prm_iter

        # Ensure that PRMContainter section is a DataFrame and not None
        df = getattr(self, name)
        if df is None:
            df = pd.DataFrame()
            setattr(self, name, df)
            self._process_df(df, name)

        # Extract, parse and write the values
        for i, prm_dict in enumerate(prm_iter):
            try:  # Extract the appropiate values
                index = prm_dict['atoms']
                value_gen = (prm_dict[k] for k in key)
            except KeyError as ex:
                raise KeyError(f"Failed to extract the {ex!r} key from "
                               f"{key_path[-1]!r} block {i}") from ex

            # Sanitize the values and convert them into appropiate units
            iterator = zip(value_gen, unit, default_unit)
            value_list = [parse_cp2k_value(*args) for args in iterator]

            # Post-process the values
            for i, (prm, func) in enumerate(zip(value_list, post_process)):
                if func is not None:
                    value_list[i] = func(prm)

            # Assign the values
            df.loc[index, columns] = value_list