Пример #1
0
def main(prefix, suffix="pos", unitconv="1.0"):

    ipos = []
    imode = []
    for filename in sorted(glob.glob(prefix + "." + suffix + "*")):
        imode.append(filename.split(".")[-1])
        ipos.append(open(filename, "r"))

    nbeads = len(ipos)
    natoms = 0
    ifr = 0
    while True:
        try:
            for i in range(nbeads):
                ret = read_file(imode[i], ipos[i])
                pos = ret["atoms"]
                cell = ret["cell"]
                if natoms == 0:
                    natoms = pos.natoms
                    beads = Beads(natoms, nbeads)
                cell.h *= float(unitconv)
                beads[i].q = pos.q * float(unitconv)
                beads.names = pos.names
        except EOFError:  # finished reading files
            sys.exit(0)

        print_file_path("pdb", beads, cell)
        ifr += 1
Пример #2
0
def main(prefix, suffix="pos", unitconv="1.0"):

    ipos = []
    imode = []
    for filename in sorted(glob.glob(prefix + "." + suffix + "*")):
        imode.append(filename.split(".")[-1])
        ipos.append(open(filename, "r"))

    nbeads = len(ipos)
    natoms = 0
    ifr = 0
    while True:
        try:
            for i in range(nbeads):
                ret = read_file(imode[i], ipos[i])
                pos = ret["atoms"]
                cell = ret["cell"]
                if natoms == 0:
                    natoms = pos.natoms
                    beads = Beads(natoms, nbeads)
                cell.h *= float(unitconv)
                beads[i].q = pos.q * float(unitconv)
                beads.names = pos.names
        except EOFError:  # finished reading files
            sys.exit(0)

        print_file_path("pdb", beads, cell)
        ifr += 1
Пример #3
0
def main(prefix, temp):

   temp = unit_to_internal("energy","kelvin",float(temp))

   ipos=[]
   for filename in sorted(glob.glob(prefix+".pos*")):
      ipos.append(open(filename,"r"))

   ifor=[]
   for filename in sorted(glob.glob(prefix+".for*")):
      ifor.append(open(filename,"r"))

   ikin=open(prefix+".kin.xyz","w")
   ikod=open(prefix+".kod.xyz","w")

   nbeads = len(ipos)
   if (nbeads!=len(ifor)): raise ValueError("Mismatch between number of output files for forces and positions")
   natoms = 0
   ifr = 0
   while True:
      try:
         for i in range(nbeads):
            pos = read_xyz(ipos[i])
            force = read_xyz(ifor[i])
            if natoms == 0:
               natoms = pos.natoms
               beads = Beads(natoms,nbeads)
               forces = Beads(natoms,nbeads)
               kcv = np.zeros((natoms,6),float)
            beads[i].q = pos.q
            forces[i].q = force.q
      except EOFError: # finished reading files
         sys.exit(0)

      q = depstrip(beads.q)
      f = depstrip(forces.q)
      qc = depstrip(beads.qc)
      kcv[:]=0
      for j in range(nbeads):
         for i in range(natoms):
            kcv[i,0] += (q[j,i*3+0]-qc[i*3+0])*f[j,i*3+0]
            kcv[i,1] += (q[j,i*3+1]-qc[i*3+1])*f[j,i*3+1]
            kcv[i,2] += (q[j,i*3+2]-qc[i*3+2])*f[j,i*3+2]
            kcv[i,3] += (q[j,i*3+0]-qc[i*3+0])*f[j,i*3+1] + (q[j,i*3+1]-qc[i*3+1])*f[j,i*3+0]
            kcv[i,4] += (q[j,i*3+0]-qc[i*3+0])*f[j,i*3+2] + (q[j,i*3+2]-qc[i*3+2])*f[j,i*3+0]
            kcv[i,5] += (q[j,i*3+1]-qc[i*3+1])*f[j,i*3+2] + (q[j,i*3+2]-qc[i*3+2])*f[j,i*3+1]
      kcv*=-0.5/nbeads
      kcv[:,0:3]+=0.5*Constants.kb*temp
      kcv[:,3:6]*=0.5

      ikin.write("%d\n# Centroid-virial kinetic energy estimator [a.u.] - diagonal terms: xx yy zz\n" % (natoms))
      ikod.write("%d\n# Centroid-virial kinetic energy estimator [a.u.] - off-diag terms: xy xz yz\n" % (natoms))
      for i in range(natoms):
         ikin.write("%8s %12.5e %12.5e %12.5e\n" % (pos.names[i], kcv[i,0], kcv[i,1], kcv[i,2]))
         ikod.write("%8s %12.5e %12.5e %12.5e\n" % (pos.names[i], kcv[i,3], kcv[i,4], kcv[i,5]))

      ifr+=1
Пример #4
0
def init_beads(iif, nbeads):
    """A file to initialize a beads object from an appropriate initializer
   object.

   Args:
      iif: An Initializer object which has information on the bead positions.
      nbeads: The number of beads.

   Raises:
      ValueError: If called using an Initializer object with a 'manual' mode.
   """

    mode = iif.mode
    value = iif.value
    if mode == "xyz" or mode == "pdb":
        if mode == "xyz": ratoms = init_xyz(value)
        if mode == "pdb": ratoms = init_pdb(value)[0]
        rbeads = Beads(ratoms[0].natoms, len(ratoms))
        for i in range(len(ratoms)):
            rbeads[i] = ratoms[i]
    elif mode == "chk":
        rbeads = init_chk(value)[0]
    elif mode == "manual":
        raise ValueError("Cannot initialize manually a whole beads object.")

    return rbeads
Пример #5
0
def init_beads(iif,
               nbeads,
               dimension="length",
               units="automatic",
               cell_units="automatic"):
    """Initializes a beads object from an appropriate initializer object.

    Args:
       iif: An Initializer object which has information on the bead positions.
       nbeads: The number of beads.

    Raises:
       ValueError: If called using an Initializer object with a 'manual' mode.
    """

    mode = iif.mode
    value = iif.value
    if mode == "chk":
        rbeads = init_chk(value)[0]
    elif mode == "manual":
        raise ValueError("Cannot initialize manually a whole beads object.")
    else:
        ret = init_file(mode, value, dimension, units, cell_units)
        ratoms = ret[0]
        rbeads = Beads(ratoms[0].natoms, len(ratoms))
        for i in range(len(ratoms)):
            rbeads[i] = ratoms[i]

    return rbeads
Пример #6
0
    def bind(self, dumop, discretization):

        self.temp = dumop.temp
        self.fix = Fix(dumop.beads.natoms, dumop.fixatoms, dumop.beads.nbeads)
        self.dbeads = Beads(dumop.beads.natoms - len(dumop.fixatoms), dumop.beads.nbeads)
        self.dbeads.q[:] = self.fix.get_active_vector(dumop.beads.copy().q, 1)
        self.dbeads.m[:] = self.fix.get_active_vector(dumop.beads.copy().m, 0)
        self.dbeads.names[:] = self.fix.get_active_vector(dumop.beads.copy().names, 0)
        self.set_coef(discretization)

        if dumop.options["mode"] == 'rate':
            self.omega2 = (self.temp * (2 * self.dbeads.nbeads) * units.Constants.kb / units.Constants.hbar) ** 2
        elif dumop.options["mode"] == 'splitting':
            self.omega2 = (self.temp * self.dbeads.nbeads * units.Constants.kb / units.Constants.hbar) ** 2

        if dumop.options["opt"] == 'nichols' or dumop.options["opt"] == 'NR' or dumop.options["opt"] == 'lanczos':
            self.h = self.spring_hessian(natoms=self.dbeads.natoms, nbeads=self.dbeads.nbeads, m3=self.dbeads.m3[0], omega2=self.omega2, coef=self.coef)
Пример #7
0
    def init_stage1(self, simul):
        """Initializes the simulation -- first stage.

      Takes a simulation object, and uses all the data in the initialization
      queue to fill up the beads and cell data needed to run the simulation.

      Args:
         simul: A simulation object to be initialized.

      Raises:
         ValueError: Raised if there is a problem with the initialization,
            if something that should have been has not been, or if the objects
            that have been specified are not compatible with each other.
      """

        if simul.beads.nbeads == 0:
            fpos = fmom = fmass = flab = fcell = False  # we don't have an explicitly defined beads object yet
        else:
            fpos = fmom = fmass = flab = fcell = True

        for (k, v) in self.queue:
            info(" # Initializer (stage 1) parsing " + str(k) + " object.",
                 verbosity.high)

            if k == "cell":
                if fcell:
                    warning("Overwriting previous cell parameters",
                            verbosity.medium)
                if v.mode == "pdb":
                    rh = init_pdb(v.value)[1].h
                elif v.mode == "chk":
                    rh = init_chk(v.value)[1].h
                else:
                    rh = v.value.reshape((3, 3))
                rh *= unit_to_internal("length", v.units, 1.0)

                simul.cell.h = rh
                if simul.cell.V == 0.0:
                    ValueError("Cell provided has zero volume")

                fcell = True
            elif k == "masses":
                if simul.beads.nbeads == 0:
                    raise ValueError(
                        "Cannot initialize the masses before the size of the system is known"
                    )
                if fmass:
                    warning("Overwriting previous atomic masses",
                            verbosity.medium)
                if v.mode == "manual":
                    rm = v.value
                else:
                    rm = init_beads(v, self.nbeads).m
                rm *= unit_to_internal("mass", v.units, 1.0)

                if v.bead < 0:  # we are initializing the path
                    if (fmom and fmass):
                        warning(
                            "Rescaling momenta to make up for changed mass",
                            verbosity.medium)
                        simul.beads.p /= simul.beads.sm3  # go to mass-scaled momenta, that are mass-invariant
                    if v.index < 0:
                        simul.beads.m = rm
                    else:  # we are initializing a specific atom
                        simul.beads.m[v.index:v.index + 1] = rm
                    if (fmom and fmass):  # finishes correcting the momenta
                        simul.beads.p *= simul.beads.sm3  # back to normal momenta
                else:
                    raise ValueError("Cannot change the mass of a single bead")
                fmass = True

            elif k == "labels":
                if simul.beads.nbeads == 0:
                    raise ValueError(
                        "Cannot initialize the labels before the size of the system is known"
                    )
                if flab:
                    warning("Overwriting previous atomic labels",
                            verbosity.medium)
                if v.mode == "manual":
                    rn = v.value
                else:
                    rn = init_beads(v, self.nbeads).names

                if v.bead < 0:  # we are initializing the path
                    if v.index < 0:
                        simul.beads.names = rn
                    else:  # we are initializing a specific atom
                        simul.beads.names[v.index:v.index + 1] = rn
                else:
                    raise ValueError(
                        "Cannot change the label of a single bead")
                flab = True

            elif k == "positions":
                if fpos:
                    warning("Overwriting previous atomic positions",
                            verbosity.medium)
                # read the atomic positions as a vector
                rq = init_vector(v, self.nbeads)
                rq *= unit_to_internal("length", v.units, 1.0)
                (nbeads, natoms) = rq.shape
                natoms /= 3

                # check if we must initialize the simulation beads
                if simul.beads.nbeads == 0:
                    if v.index >= 0:
                        raise ValueError(
                            "Cannot initialize single atoms before the size of the system is known"
                        )
                    simul.beads.resize(natoms, self.nbeads)

                set_vector(v, simul.beads.q, rq)
                fpos = True

            elif (
                    k == "velocities" or k == "momenta"
            ) and v.mode == "thermal":  # intercept here thermal initialization, so we don't need to check further down
                if fmom:
                    warning("Overwriting previous atomic momenta",
                            verbosity.medium)
                if simul.beads.natoms == 0:
                    raise ValueError(
                        "Cannot initialize momenta before the size of the system is known."
                    )
                if not fmass:
                    raise ValueError(
                        "Trying to resample velocities before having masses.")

                rtemp = v.value * unit_to_internal("temperature", v.units, 1.0)
                if rtemp <= 0:
                    warning(
                        "Using the simulation temperature to resample velocities",
                        verbosity.low)
                    rtemp = simul.ensemble.temp
                else:
                    info(
                        " # Resampling velocities at temperature %s %s" %
                        (v.value, v.units), verbosity.low)

                # pull together a mock initialization to get NM masses right
                #without too much code duplication
                if v.bead >= 0:
                    raise ValueError("Cannot thermalize a single bead")
                if v.index >= 0:
                    rnatoms = 1
                else:
                    rnatoms = simul.beads.natoms
                rbeads = Beads(rnatoms, simul.beads.nbeads)
                if v.index < 0:
                    rbeads.m[:] = simul.beads.m
                else:
                    rbeads.m[:] = simul.beads.m[v.index]
                rnm = NormalModes(mode=simul.nm.mode,
                                  transform_method=simul.nm.transform_method,
                                  freqs=simul.nm.nm_freqs)
                rens = Ensemble(dt=simul.ensemble.dt, temp=simul.ensemble.temp)
                rnm.bind(rbeads, rens)
                # then we exploit the sync magic to do a complicated initialization
                # in the NM representation
                # with (possibly) shifted-frequencies NM
                rnm.pnm = simul.prng.gvec(
                    (rbeads.nbeads, 3 * rbeads.natoms)) * np.sqrt(
                        rnm.dynm3) * np.sqrt(
                            rbeads.nbeads * rtemp * Constants.kb)

                if v.index < 0:
                    simul.beads.p = rbeads.p
                else:
                    simul.beads.p[:, 3 * v.index:3 * (v.index + 1)] = rbeads.p
                fmom = True

            elif k == "momenta":
                if fmom:
                    warning("Overwriting previous atomic momenta",
                            verbosity.medium)
                # read the atomic momenta as a vector
                rp = init_vector(v, self.nbeads, momenta=True)
                rp *= unit_to_internal("momentum", v.units, 1.0)
                (nbeads, natoms) = rp.shape
                natoms /= 3

                # checks if we must initialize the simulation beads
                if simul.beads.nbeads == 0:
                    if v.index >= 0:
                        raise ValueError(
                            "Cannot initialize single atoms before the size of the system is known"
                        )
                    simul.beads.resize(natoms, self.nbeads)

                rp *= np.sqrt(self.nbeads / nbeads)
                set_vector(v, simul.beads.p, rp)
                fmom = True

            elif k == "velocities":
                if fmom:
                    warning("Overwriting previous atomic momenta",
                            verbosity.medium)
                # read the atomic velocities as a vector
                rv = init_vector(v, self.nbeads)
                rv *= unit_to_internal("velocity", v.units, 1.0)
                (nbeads, natoms) = rv.shape
                natoms /= 3

                # checks if we must initialize the simulation beads
                if simul.beads.nbeads == 0 or not fmass:
                    ValueError(
                        "Cannot initialize velocities before the masses of the atoms are known"
                    )
                    simul.beads.resize(natoms, self.nbeads)

                warning(
                    "Initializing from velocities uses the previously defined masses -- not the masses inferred from the file -- to build momenta",
                    verbosity.low)
                if v.index >= 0:
                    rv *= simul.beads.m[v.index]
                elif v.bead >= 0:
                    rv *= simul.beads.m3[0]
                else:
                    rv *= simul.beads.m3
                rv *= np.sqrt(self.nbeads / nbeads)
                set_vector(v, simul.beads.p, rv)
                fmom = True
            elif k == "thermostat":
                pass  # thermostats must be initialized in a second stage

        if simul.beads.natoms == 0:
            raise ValueError(
                "Initializer could not initialize the atomic positions")
        if simul.cell.V == 0:
            raise ValueError("Initializer could not initialize the cell")
        for i in range(simul.beads.natoms):
            if simul.beads.m[i] <= 0:
                raise ValueError("Initializer could not initialize the masses")
            if simul.beads.names[i] == "":
                raise ValueError(
                    "Initializer could not initialize the atom labels")
        if not fmom:
            warning(
                "Momenta not specified in initialize. Will start with zero velocity if they are not specified in beads.",
                verbosity.low)
Пример #8
0
    def init_stage1(self, simul):
        """Initializes the simulation -- first stage.

        Takes a simulation object, and uses all the data in the initialization
        queue to fill up the beads and cell data needed to run the simulation.

        Args:
           simul: A simulation object to be initialized.

        Raises:
           ValueError: Raised if there is a problem with the initialization,
              if something that should have been has not been, or if the objects
              that have been specified are not compatible with each other.
        """

        if simul.beads.nbeads == 0:
            fpos = fmom = fmass = flab = fcell = False   # we don't have an explicitly defined beads object yet
        else:
            fpos = fmom = fmass = flab = fcell = True

        for (k, v) in self.queue:
            info(" # Initializer (stage 1) parsing " + str(k) + " object.", verbosity.high)

            if k == "cell":
                if v.mode == "manual":
                    rh = v.value.reshape((3, 3)) * unit_to_internal("length", v.units, 1.0)
                elif v.mode == "chk":
                    rh = init_chk(v.value)[1].h
                elif init_file(v.mode, v.value)[1].h.trace() == -3:
                    # In case the file do not contain any
                    # + cell parameters, the diagonal elements of the cell will be
                    # +set to -1 from the io_units and nothing is read here.
                    continue
                else:
                    rh = init_file(v.mode, v.value, cell_units=v.units)[1].h

                if fcell:
                    warning("Overwriting previous cell parameters", verbosity.low)

                simul.cell.h = rh
                if simul.cell.V == 0.0:
                    ValueError("Cell provided has zero volume")

                fcell = True
            elif k == "masses":
                if simul.beads.nbeads == 0:
                    raise ValueError("Cannot initialize the masses before the size of the system is known")
                if fmass:
                    warning("Overwriting previous atomic masses", verbosity.medium)
                if v.mode == "manual":
                    rm = v.value * unit_to_internal("mass", v.units, 1.0)
                else:
                    rm = init_beads(v, self.nbeads).m

                if v.bead < 0:   # we are initializing the path
                    if (fmom and fmass):
                        warning("Rescaling momenta to make up for changed mass", verbosity.medium)
                        simul.beads.p /= simul.beads.sm3   # go to mass-scaled momenta, that are mass-invariant
                    if v.index < 0:
                        simul.beads.m = rm
                    else:  # we are initializing a specific atom
                        simul.beads.m[v.index:v.index + 1] = rm
                    if (fmom and fmass):  # finishes correcting the momenta
                        simul.beads.p *= simul.beads.sm3  # back to normal momenta
                else:
                    raise ValueError("Cannot change the mass of a single bead")
                fmass = True

            elif k == "labels":
                if simul.beads.nbeads == 0:
                    raise ValueError("Cannot initialize the labels before the size of the system is known")
                if flab:
                    warning("Overwriting previous atomic labels", verbosity.medium)
                if v.mode == "manual":
                    rn = v.value
                else:
                    rn = init_beads(v, self.nbeads).names

                if v.bead < 0:   # we are initializing the path
                    if v.index < 0:
                        simul.beads.names = rn
                    else:  # we are initializing a specific atom
                        simul.beads.names[v.index:v.index + 1] = rn
                else:
                    raise ValueError("Cannot change the label of a single bead")
                flab = True

            elif k == "positions":
                if fpos:
                    warning("Overwriting previous atomic positions", verbosity.medium)
                # read the atomic positions as a vector

                rq = init_vector(v, self.nbeads, dimension="length", units=v.units)

                nbeads, natoms = rq.shape
                natoms /= 3

                # check if we must initialize the simulation beads
                if simul.beads.nbeads == 0:
                    if v.index >= 0:
                        raise ValueError("Cannot initialize single atoms before the size of the system is known")
                    simul.beads.resize(natoms, self.nbeads)

                set_vector(v, simul.beads.q, rq)
                fpos = True

            elif (k == "velocities" or k == "momenta") and v.mode == "thermal":   # intercept here thermal initialization, so we don't need to check further down
                if fmom:
                    warning("Overwriting previous atomic momenta", verbosity.medium)
                if simul.beads.natoms == 0:
                    raise ValueError("Cannot initialize momenta before the size of the system is known.")
                if not fmass:
                    raise ValueError("Trying to resample velocities before having masses.")

                rtemp = v.value * unit_to_internal("temperature", v.units, 1.0)
                if rtemp <= 0:
                    warning("Using the simulation temperature to resample velocities", verbosity.low)
                    rtemp = simul.ensemble.temp
                else:
                    info(" # Resampling velocities at temperature %s %s" % (v.value, v.units), verbosity.low)

                # pull together a mock initialization to get NM masses right
                # without too much code duplication
                if v.bead >= 0:
                    raise ValueError("Cannot thermalize a single bead")
                if v.index >= 0:
                    rnatoms = 1
                else:
                    rnatoms = simul.beads.natoms
                rbeads = Beads(rnatoms, simul.beads.nbeads)
                if v.index < 0:
                    rbeads.m[:] = simul.beads.m
                else:
                    rbeads.m[:] = simul.beads.m[v.index]
                rnm = NormalModes(mode=simul.nm.mode, transform_method=simul.nm.transform_method, freqs=simul.nm.nm_freqs)
                rens = Ensemble(temp=simul.ensemble.temp)
                rmv = Motion()
                rnm.bind(rens, rmv, rbeads)
                # then we exploit the sync magic to do a complicated initialization
                # in the NM representation
                # with (possibly) shifted-frequencies NM
                rnm.pnm = simul.prng.gvec((rbeads.nbeads, 3 * rbeads.natoms)) * np.sqrt(rnm.dynm3) * np.sqrt(rbeads.nbeads * rtemp * Constants.kb)

                if v.index < 0:
                    simul.beads.p = rbeads.p
                else:
                    simul.beads.p[:, 3 * v.index:3 * (v.index + 1)] = rbeads.p
                fmom = True

            elif k == "momenta":
                if fmom:
                    warning("Overwriting previous atomic momenta", verbosity.medium)
                # read the atomic momenta as a vector
                rp = init_vector(v, self.nbeads, momenta=True, dimension="momentum", units=v.units)
                nbeads, natoms = rp.shape
                natoms /= 3

                # checks if we must initialize the simulation beads
                if simul.beads.nbeads == 0:
                    if v.index >= 0:
                        raise ValueError("Cannot initialize single atoms before the size of the system is known")
                    simul.beads.resize(natoms, self.nbeads)

                rp *= np.sqrt(self.nbeads / nbeads)
                set_vector(v, simul.beads.p, rp)
                fmom = True
            elif k == "velocities":
                if fmom:
                    warning("Overwriting previous atomic momenta", verbosity.medium)
                # read the atomic velocities as a vector
                rv = init_vector(v, self.nbeads, dimension="velocity", units=v.units)
                nbeads, natoms = rv.shape
                natoms /= 3

                # checks if we must initialize the simulation beads
                if simul.beads.nbeads == 0 or not fmass:
                    ValueError("Cannot initialize velocities before the masses of the atoms are known")
                    simul.beads.resize(natoms, self.nbeads)

                warning("Initializing from velocities uses the previously defined masses -- not the masses inferred from the file -- to build momenta", verbosity.low)
                if v.index >= 0:
                    rv *= simul.beads.m[v.index]
                else:
                    for ev in rv:
                        ev *= simul.beads.m3[0]
                rv *= np.sqrt(self.nbeads / nbeads)
                set_vector(v, simul.beads.p, rv)
                fmom = True
            elif k == "gle": pass   # thermostats must be initialised in a second stage

        if simul.beads.natoms == 0:
            raise ValueError("Initializer could not initialize the atomic positions")
        if simul.cell.V == 0:
            raise ValueError("Initializer could not initialize the cell")
        for i in range(simul.beads.natoms):
            if simul.beads.m[i] <= 0:
                raise ValueError("Initializer could not initialize the masses")
            if simul.beads.names[i] == "":
                raise ValueError("Initializer could not initialize the atom labels")
        if not fmom:
            warning("Momenta not specified in initialize. Will start with zero velocity if they are not specified in beads.", verbosity.low)
Пример #9
0
    def bind(self, beads, cell, fcomponents, fflist):
        """Binds beads, cell and forces to the forcefield.


        Args:
           beads: Beads object from which the bead positions are taken.
           cell: Cell object from which the system box is taken.
           fcomponents: A list of different objects for each force type.
              For example, if ring polymer contraction is being used,
              then there may be separate forces for the long and short
              range part of the potential.
           fflist: A list of forcefield objects to use to calculate the potential,
              forces and virial for each force type. To clarify: fcomponents are the
              names and parameters of forcefields that are active for a certain
              system. fflist contains the overall list of force providers,
              and one typically has just one per force kind.
        """

        self.natoms = beads.natoms
        self.nbeads = beads.nbeads
        self.beads = beads
        self.cell = cell
        self.bound = True
        self.nforces = len(fcomponents)
        self.fcomp = fcomponents
        self.ff = fflist

        # fflist should be a dictionary of forcefield objects
        self.mforces = []
        self.mbeads = []
        self.mrpc = []

        dself = dd(self)

        # a "function factory" to generate functions to automatically update
        # contracted paths
        def make_rpc(rpc, beads):
            return lambda: rpc.b1tob2(dstrip(beads.q))

        # creates new force objects, possibly acting on contracted path
        # representations
        for fc in self.fcomp:

            # creates an automatically-updated contracted beads object
            newb = fc.nbeads
            # if the number of beads for this force component is unspecified,
            # assume full force evaluation
            if newb == 0 or newb > beads.nbeads: newb = beads.nbeads
            newforce = ForceComponent(ffield=fc.ffield, name=fc.name, nbeads=newb, weight=fc.weight, mts_weights=fc.mts_weights, epsilon=fc.epsilon)
            newbeads = Beads(beads.natoms, newb)
            newrpc = nm_rescale(beads.nbeads, newb)

            # the beads positions for this force components are obtained
            # automatically, when needed, as a contraction of the full beads
            dd(newbeads).q._func = make_rpc(newrpc, beads)
            for b in newbeads:
                # must update also indirect access to the beads coordinates
                dd(b).q._func = dd(newbeads).q._func

            # makes newbeads.q depend from beads.q
            dd(beads).q.add_dependant(dd(newbeads).q)

            # now we create a new forcecomponent which is bound to newbeads!
            newforce.bind(newbeads, cell, fflist)

            # adds information we will later need to the appropriate lists.
            self.mbeads.append(newbeads)
            self.mforces.append(newforce)
            self.mrpc.append(newrpc)

        # now must expose an interface that gives overall forces
        dself.f = depend_array(name="f", value=np.zeros((self.nbeads, 3 * self.natoms)),
                               func=self.f_combine,
                               dependencies=[dd(ff).f for ff in self.mforces])

        # collection of pots and virs from individual ff objects
        dself.pots = depend_array(name="pots", value=np.zeros(self.nbeads, float),
                                  func=self.pot_combine,
                                  dependencies=[dd(ff).pots for ff in self.mforces])

        # must take care of the virials!
        dself.virs = depend_array(name="virs", value=np.zeros((self.nbeads, 3, 3), float),
                                  func=self.vir_combine,
                                  dependencies=[dd(ff).virs for ff in self.mforces])

        dself.extras = depend_value(name="extras", value=np.zeros(self.nbeads, float),
                                    func=self.extra_combine,
                                    dependencies=[dd(ff).extras for ff in self.mforces])

        # total potential and total virial
        dself.pot = depend_value(name="pot", func=(lambda: self.pots.sum()),
                                 dependencies=[dself.pots])

        dself.vir = depend_array(name="vir", func=self.get_vir, value=np.zeros((3, 3)),
                                 dependencies=[dself.virs])

        # SC forces and potential
        dself.alpha = depend_value(name="alpha", value=0.0)

        # The number of MTS levels
        dself.nmtslevels = depend_value(name="nmtslevels", value=0, func=self.get_nmtslevels)

        # This will be piped from normalmodes
        dself.omegan2 = depend_value(name="omegan2", value=0)

        # The Suzuki-Chin difference potential
        dself.potssc = depend_array(name="potssc", value=np.zeros(self.nbeads, float),
                                    dependencies=[dd(self.beads).m, dself.f, dself.pots, dself.alpha,
                                                  dself.omegan2],
                                    func=self.get_potssc)

        dself.potsc = depend_value(name="potsc",
                                   dependencies=[dself.potssc],
                                   func=(lambda: self.potssc.sum()))

        # The coefficients of the physical and the |f|^2 terms
        dself.coeffsc_part_1 = depend_array(name="coeffsc_part_1", value=np.zeros((self.nbeads, 1), float),
                                            func=self.get_coeffsc_part_1)

        dself.coeffsc_part_2 = depend_array(name="coeffsc_part_2", value=np.zeros((self.nbeads, 1), float),
                                            dependencies=[dself.alpha, dself.omegan2], func=self.get_coeffsc_part_2)

        # A list that contains the high order component of the force and the virial
        dself.fvir_4th_order = depend_value(name="fvir_4th_order", value=[None, None],
                                            dependencies=[dd(self.beads).m, dself.f, dself.pots],
                                            func=self.fvir_4th_order_combine)

        # The high order component of the Suzuki-Chin force.
        dself.f_4th_order = depend_array(name="f_4th_order", value=np.zeros((self.nbeads, 3 * self.natoms), float),
                                         dependencies=[dself.fvir_4th_order],
                                         func=(lambda: self.fvir_4th_order[0]))

        dself.fsc_part_1 = depend_array(name="fsc_part_1", value=np.zeros((self.nbeads, 3 * self.natoms), float),
                                        dependencies=[dself.coeffsc_part_1, dself.f],
                                        func=self.get_fsc_part_1)

        dself.fsc_part_2 = depend_array(name="fsc_part_2", value=np.zeros((self.nbeads, 3 * self.natoms), float),
                                        dependencies=[dself.coeffsc_part_2, dself.f_4th_order],
                                        func=self.get_fsc_part_2)

        dself. fsc = depend_array(name="fsc", value=np.zeros((self.nbeads, 3 * self.natoms), float),
                                  dependencies=[dself.fsc_part_1, dself.fsc_part_2],
                                  func=self.get_fsc)

        # The high order component of the Suzuki-Chin virial.
        dself.virs_4th_order = depend_array(name="vir_4th_order", value=np.zeros((self.nbeads, 3, 3), float),
                                            dependencies=[dself.fvir_4th_order],
                                            func=(lambda: self.fvir_4th_order[1]))

        dself.virssc_part_1 = depend_array(name="virssc_part_1", value=np.zeros((self.nbeads, 3, 3), float),
                                           dependencies=[dself.coeffsc_part_1, dself.virs],
                                           func=self.get_virssc_part_1)

        dself.virssc_part_2 = depend_array(name="virssc_part_2", value=np.zeros((self.nbeads, 3, 3), float),
                                           dependencies=[dself.coeffsc_part_2, dself.virs_4th_order],
                                           func=self.get_virssc_part_2)

        dself.virssc = depend_array(name="virssc", value=np.zeros((self.nbeads, 3, 3), float),
                                    dependencies=[dself.virssc_part_1, dself.virssc_part_2],
                                    func=self.get_virssc)

        dself.virsc = depend_value(name="potsc",
                                   dependencies=[dself.potssc],
                                   func=(lambda: np.sum(self.virssc, axis=0)))

        # Add dependencies from the force weights, that are applied here when the total
        # force is assembled from its components

        for fc in self.mforces:
            dself.f.add_dependency(dd(fc).weight)
            dself.pots.add_dependency(dd(fc).weight)
            dself.virs.add_dependency(dd(fc).weight)
def main(prefix, temp):

    temp = unit_to_internal("energy", "kelvin", float(temp))

    ipos = []
    for filename in sorted(glob.glob(prefix + ".pos*")):
        ipos.append(open(filename, "r"))

    ifor = []
    for filename in sorted(glob.glob(prefix + ".for*")):
        ifor.append(open(filename, "r"))

    ivacfim = open(prefix + ".imvacf", "w")

    nbeads = len(ipos)

    if (nbeads != len(ifor)):
        raise ValueError(
            "Mismatch between number of output files for forces and positions")
    natoms = 0
    ifr = 0
    while True:
        try:
            for i in range(nbeads):
                ret = read_file("xyz", ipos[i])
                pos = ret["atoms"]
                ret = read_file("xyz", ifor[i])
                force = ret["atoms"]
                if natoms == 0:
                    natoms = pos.natoms
                    beads = Beads(natoms, nbeads)
                    forces = Beads(natoms, nbeads)
                beads[i].q = pos.q
                beads[i].m = pos.m
                forces[i].q = force.q
        except EOFError:  # finished reading files
            break

        if (ifr == 0):
            cim = np.zeros((natoms, nbeads + 1), float)

        q = dstrip(beads.q)
        f = dstrip(forces.q)
        m = dstrip(beads.m)
        qc = dstrip(beads.qc)

        for j in range(nbeads + 1):
            for i in range(natoms):
                dummy = [(q[(j + k) % nbeads, 3 * i:3 *
                            (i + 1)] - qc[3 * i:3 * (i + 1)]) *
                         (-f[k, 3 * i:3 * (i + 1)]) for k in range(nbeads)]
                cim[i, j] = cim[i, j] + np.sum(dummy) / (nbeads * m[i])
                cim[i, j] += 3. * Constants.kb * temp / m[i]

        ifr += 1
        print 'Frame: ', ifr

    cim[:, :] = cim[:, :] / ifr

    fullcim = np.zeros(len(cim))
    for j in range(nbeads + 1):
        fullcim[j] = np.sum([i for i in cim[:, j]])

    ivacfim.write(
        "# Imaginary time autocorrelation, averaged through the whole simulation -- beta*hbar is %f \n"
        % (Constants.hbar / (Constants.kb * temp)))

    for islice in range(nbeads + 1):
        ivacfim.write("%f %12.5e \n" %
                      (float(islice) / float(nbeads), fullcim[islice]))
Пример #11
0
def main(prefix, temp):

    T = float(temp)
    fns_pos = sorted(glob.glob(prefix + ".pos*"))
    fns_for = sorted(glob.glob(prefix + ".for*"))
    fn_out_kin = prefix + ".kin.xyz"
    fn_out_kod = prefix + ".kod.xyz"

    # check that we found the same number of positions and forces files
    nbeads = len(fns_pos)
    if nbeads != len(fns_for):
        print fns_pos
        print fns_for
        raise ValueError(
            "Mismatch between number of input files for forces and positions.")

    # print some information
    print 'temperature = {:f} K'.format(T)
    print
    print 'number of beads = {:d}'.format(nbeads)
    print
    print 'positions and forces file names:'
    for fn_pos, fn_for in zip(fns_pos, fns_for):
        print '{:s}   {:s}'.format(fn_pos, fn_for)
    print
    print 'output file names:'
    print fn_out_kin
    print fn_out_kod
    print

    temp = unit_to_internal("energy", "kelvin", T)

    # open input and output files
    ipos = [open(fn, "r") for fn in fns_pos]
    ifor = [open(fn, "r") for fn in fns_for]
    ikin = open(fn_out_kin, "w")
    ikod = open(fn_out_kod, "w")

    natoms = 0
    ifr = 0
    while True:

        # print progress
        if ifr % 100 == 0:
            print '\rProcessing frame {:d}'.format(ifr),
            sys.stdout.flush()

        # load one frame
        try:
            for i in range(nbeads):
                ret = read_file("xyz", ipos[i])
                pos = ret["atoms"]
                ret = read_file("xyz", ifor[i])
                force = ret["atoms"]
                if natoms == 0:
                    natoms = pos.natoms
                    beads = Beads(natoms, nbeads)
                    forces = Beads(natoms, nbeads)
                    kcv = np.zeros((natoms, 6), float)
                beads[i].q = pos.q
                forces[i].q = force.q
        except EOFError:
            # finished reading files
            break

        # calculate kinetic energies
        q = dstrip(beads.q)
        f = dstrip(forces.q)
        qc = dstrip(beads.qc)
        kcv[:] = 0
        for j in range(nbeads):
            for i in range(natoms):
                kcv[i,
                    0] += (q[j, i * 3 + 0] - qc[i * 3 + 0]) * f[j, i * 3 + 0]
                kcv[i,
                    1] += (q[j, i * 3 + 1] - qc[i * 3 + 1]) * f[j, i * 3 + 1]
                kcv[i,
                    2] += (q[j, i * 3 + 2] - qc[i * 3 + 2]) * f[j, i * 3 + 2]
                kcv[i, 3] += (
                    q[j, i * 3 + 0] - qc[i * 3 + 0]) * f[j, i * 3 + 1] + (
                        q[j, i * 3 + 1] - qc[i * 3 + 1]) * f[j, i * 3 + 0]
                kcv[i, 4] += (
                    q[j, i * 3 + 0] - qc[i * 3 + 0]) * f[j, i * 3 + 2] + (
                        q[j, i * 3 + 2] - qc[i * 3 + 2]) * f[j, i * 3 + 0]
                kcv[i, 5] += (
                    q[j, i * 3 + 1] - qc[i * 3 + 1]) * f[j, i * 3 + 2] + (
                        q[j, i * 3 + 2] - qc[i * 3 + 2]) * f[j, i * 3 + 1]
        kcv *= -0.5 / nbeads
        kcv[:, 0:3] += 0.5 * Constants.kb * temp
        kcv[:, 3:6] *= 0.5

        # write output
        ikin.write(
            "%d\n# Centroid-virial kinetic energy estimator [a.u.] - diagonal terms: xx yy zz\n"
            % natoms)
        ikod.write(
            "%d\n# Centroid-virial kinetic energy estimator [a.u.] - off-diag terms: xy xz yz\n"
            % natoms)
        for i in range(natoms):
            ikin.write("%8s %12.5e %12.5e %12.5e\n" %
                       (pos.names[i], kcv[i, 0], kcv[i, 1], kcv[i, 2]))
            ikod.write("%8s %12.5e %12.5e %12.5e\n" %
                       (pos.names[i], kcv[i, 3], kcv[i, 4], kcv[i, 5]))

        ifr += 1

    print '\rProcessed {:d} frames.'.format(ifr)

    ikin.close()
    ikod.close()
Пример #12
0
   def bind(self, beads, cell, fcomponents, fflist):
      """Binds beads, cell and forces to the forcefield.


      Args:
         beads: Beads object from which the bead positions are taken.
         cell: Cell object from which the system box is taken.
         fcomponents: A list of different objects for each force type.
            For example, if ring polymer contraction is being used,
            then there may be separate forces for the long and short
            range part of the potential.
         fflist: A list of forcefield objects to use to calculate the potential,
            forces and virial for each force type. To clarify: fcomponents are the
            names and parameters of forcefields that are active for a certain
            system. fflist contains the overall list of force providers,
            and one typically has just one per force kind.
      """

      self.natoms = beads.natoms
      self.nbeads = beads.nbeads
      self.beads = beads
      self.cell = cell
      self.bound = True
      self.nforces = len(fcomponents)
      self.fcomp = fcomponents
      self.ff = fflist

      # fflist should be a dictionary of forcefield objects
      self.mforces = []
      self.mbeads = []
      self.mrpc = []

      # a "function factory" to generate functions to automatically update
      #contracted paths
      def make_rpc(rpc, beads):
         return lambda: rpc.b1tob2(depstrip(beads.q))

      # creates new force objects, possibly acting on contracted path
      #representations
      for fc in self.fcomp:

         # creates an automatically-updated contracted beads object
         newb = fc.nbeads
         # if the number of beads for this force component is unspecified,
         # assume full force evaluation
         if newb == 0: newb = beads.nbeads
         newforce = ForceComponent(ffield=fc.ffield, name=fc.name, nbeads=newb, weight=fc.weight, mts_weights=fc.mts_weights)
         newbeads = Beads(beads.natoms, newb)
         newrpc = nm_rescale(beads.nbeads, newb)

         # the beads positions for this force components are obtained
         # automatically, when needed, as a contraction of the full beads
         dget(newbeads,"q")._func = make_rpc(newrpc, beads)
         for b in newbeads:
            # must update also indirect access to the beads coordinates
            dget(b,"q")._func = dget(newbeads,"q")._func

         # makes newbeads.q depend from beads.q
         dget(beads,"q").add_dependant(dget(newbeads,"q"))

         #now we create a new forcecomponent which is bound to newbeads!
         newforce.bind(newbeads, cell, fflist)

         #adds information we will later need to the appropriate lists.
         self.mbeads.append(newbeads)
         self.mforces.append(newforce)
         self.mrpc.append(newrpc)

      #now must expose an interface that gives overall forces
      dset(self,"f",
         depend_array(name="f",value=np.zeros((self.nbeads,3*self.natoms)),
            func=self.f_combine,
               dependencies=[dget(ff, "f") for ff in self.mforces] ) )

      # collection of pots and virs from individual ff objects
      dset(self,"pots",
         depend_array(name="pots", value=np.zeros(self.nbeads,float),
            func=self.pot_combine,
               dependencies=[dget(ff, "pots") for ff in self.mforces]) )

      # must take care of the virials!
      dset(self,"virs",
         depend_array(name="virs", value=np.zeros((self.nbeads,3,3),float),
            func=self.vir_combine,
               dependencies=[dget(ff, "virs") for ff in self.mforces]) )

      dset(self,"extras",
         depend_value(name="extras", value=np.zeros(self.nbeads,float),
            func=self.extra_combine,
               dependencies=[dget(ff, "extras") for ff in self.mforces]))

      # total potential and total virial
      dset(self,"pot",
         depend_value(name="pot", func=(lambda: self.pots.sum()),
            dependencies=[dget(self,"pots")]))

      dset(self,"vir",
         depend_array(name="vir", func=self.get_vir, value=np.zeros((3,3)),
            dependencies=[dget(self,"virs")]))


      # SC forces and potential
      dset(self, "alpha", depend_value(name="alpha", value=0.5))

      # this will be piped from normalmodes
      dset(self, "omegan2", depend_value(name="alpha", value=0))

      dset(self, "SCCALC",
           depend_value(name="SCCALC", func=self.sccalc, value = [None,None],
                 dependencies=[dget(self, "f"), dget(self,"pots"), dget(self,"alpha"),  dget(self,"omegan2")] ) )

      dset(self, "fsc", depend_array(name="fsc",value=np.zeros((self.nbeads,3*self.natoms)),
            dependencies=[dget(self,"SCCALC")],
            func=(lambda: self.SCCALC[1] ) ) )

      dset(self, "potsc", depend_value(name="potsc",
            dependencies=[dget(self,"SCCALC") ],
            func=(lambda: self.SCCALC[0] ) ) )
Пример #13
0
   def bind(self, beads, cell, flist):

      self.natoms = beads.natoms
      self.nbeads = beads.nbeads
      self.nforces = len(flist)

      # flist should be a list of tuples containing ( "name", forcebeads)
      self.mforces = []
      self.mbeads = []
      self.mweights = []
      self.mrpc = []

      # a "function factory" to generate functions to automatically update
      #contracted paths
      def make_rpc(rpc, beads):
         return lambda: rpc.b1tob2(depstrip(beads.q))

      # creates new force objects, possibly acting on contracted path
      #representations
      for (ftype, fbeads) in flist:

         # creates an automatically-updated contracted beads object
         newb = fbeads.nbeads
         newforce = fbeads.copy()
         newweight = fbeads.weight

         # if the number of beads for this force component is unspecified,
         #assume full force evaluation
         if newb == 0:
            newb = beads.nbeads
            newforce.nbeads = newb

         newbeads = Beads(beads.natoms, newb)
         newrpc = nm_rescale(beads.nbeads, newb)

         dget(newbeads,"q")._func = make_rpc(newrpc, beads)
         for b in newbeads:
            # must update also indirect access to the beads coordinates
            dget(b,"q")._func = dget(newbeads,"q")._func

         # makes newbeads.q depend from beads.q
         dget(beads,"q").add_dependant(dget(newbeads,"q"))

         #now we create a new forcebeads which is bound to newbeads!
         newforce.bind(newbeads, cell)

         #adds information we will later need to the appropriate lists.
         self.mweights.append(newweight)
         self.mbeads.append(newbeads)
         self.mforces.append(newforce)
         self.mrpc.append(newrpc)

      #now must expose an interface that gives overall forces
      dset(self,"f",
         depend_array(name="f",value=np.zeros((self.nbeads,3*self.natoms)),
            func=self.f_combine,
               dependencies=[dget(ff, "f") for ff in self.mforces] ) )

      # collection of pots and virs from individual ff objects
      dset(self,"pots",
         depend_array(name="pots", value=np.zeros(self.nbeads,float),
            func=self.pot_combine,
               dependencies=[dget(ff, "pots") for ff in self.mforces]) )

      # must take care of the virials!
      dset(self,"virs",
         depend_array(name="virs", value=np.zeros((self.nbeads,3,3),float),
            func=self.vir_combine,
               dependencies=[dget(ff, "virs") for ff in self.mforces]) )

      dset(self,"extras",
         depend_value(name="extras", value=np.zeros(self.nbeads,float),
            func=self.extra_combine,
               dependencies=[dget(ff, "extras") for ff in self.mforces]))

      # total potential and total virial
      dset(self,"pot",
         depend_value(name="pot", func=(lambda: self.pots.sum()),
            dependencies=[dget(self,"pots")]))
      dset(self,"vir",
         depend_array(name="vir", func=self.get_vir, value=np.zeros((3,3)),
            dependencies=[dget(self,"virs")]))