Beispiel #1
0
		def calculate(coords):
			coord_count = 0
			for s in NEB.states[1:-1]:
				for a in s:
					a.x, a.y, a.z = coords[coord_count], coords[coord_count+1], coords[coord_count+2]
					coord_count += 3
			#start DFT jobs
			running_jobs = []
			for i,state in enumerate(NEB.states[1:-1]):
				guess = '' if NEB.step==0 else ' Guess=Read'
				running_jobs.append( job('%s-%d-%d'%(NEB.name,NEB.step,i), NEB.theory+' Force'+guess, state, queue=queue, force=True, previous=('%s-%d-%d'%(NEB.name,NEB.step-1,i)) if NEB.step>0 else None, extra_section=extra_section) )
			#wait for jobs to finish
			for j in running_jobs: j.wait()
			#get forces and energies from DFT calculations
			energies = []
			for i,state in enumerate(NEB.states[1:-1]):
				try:
					new_energy, new_atoms = parse_atoms('%s-%d-%d'%(NEB.name,NEB.step,i))
				except:
					print 'Job failed: %s-%d-%d'%(NEB.name,NEB.step,i); exit()
				energies.append(new_energy)
				for a,b in zip(state, new_atoms):
					a.fx = b.fx; a.fy = b.fy; a.fz = b.fz
			dft_energies = copy.deepcopy(energies)
			#add spring forces to atoms
			for i,state in enumerate(NEB.states[1:-1]):
				for j,b in enumerate(state):
					a,c = NEB.states[i-1][j], NEB.states[i+1][j]
					if j in spring_atoms:
						b.fx += NEB.k*(a.x-b.x) + NEB.k*(c.x-b.x)
						b.fy += NEB.k*(a.y-b.y) + NEB.k*(c.y-b.y)
						b.fz += NEB.k*(a.z-b.z) + NEB.k*(c.z-b.z)
						energies[i] += 0.5*NEB.k*(utils.dist_squared(a,b) + utils.dist_squared(b,c))
			#set error
			NEB.error = sum(energies)
			#set forces
			NEB.forces = []
			for state in NEB.states[1:-1]:
				for a in state:
					NEB.forces += [-a.fx, -a.fy, -a.fz] #derivative of the error
			#increment step
			NEB.step += 1
			#write to xyz file
			NEB.xyz = open(name+'.xyz', 'w')
			for state in NEB.states:
				files.write_xyz(state, NEB.xyz)
			NEB.xyz.close()
			#print data
			print NEB.step, NEB.error, ('%10.7g '*len(dft_energies)) % tuple(dft_energies)
def remove_unattached_ligands(atoms, bonds, angles, dihedrals, spoc):
    sulfurs = [a for a in atoms if a.element == "S"]
    remove_count = 0
    atoms_to_remove = {}
    for i, a in enumerate(atoms):
        if a.element == "Pb":
            nearest_sulfur = min([utils.dist_squared(a, b) for b in sulfurs])
            if nearest_sulfur > 5 ** 2:
                # remove whole spoc, based on size of spoc and where pb is within it (always first?)
                remove_count = len(spoc.atoms)
        if remove_count > 0:
            remove_count -= 1
            atoms_to_remove[a] = True
    atoms = [a for a in atoms if a not in atoms_to_remove]
    bonds = [b for b in bonds if b.atoms[0] not in atoms_to_remove and b.atoms[1] not in atoms_to_remove]
    angles = [
        a
        for a in angles
        if a.atoms[0] not in atoms_to_remove and a.atoms[1] not in atoms_to_remove and a.atoms[2] not in atoms_to_remove
    ]
    dihedrals = [
        d
        for d in dihedrals
        if d.atoms[0] not in atoms_to_remove
        and d.atoms[1] not in atoms_to_remove
        and d.atoms[2] not in atoms_to_remove
        and d.atoms[3] not in atoms_to_remove
    ]
    return atoms, bonds, angles, dihedrals
Beispiel #3
0
	def do_route(route, limit): # return new route
		if limit == 0:
			return route
		# don't change depot
		for i in range(0, len(route)-2):
			u_1 = route[i].pos
			u_2 = route[i+1].pos
			for j in range(i+1, len(route)-1):
				v_1 = route[j].pos
				v_2 = route[j+1].pos

				if ( dist_squared(u_1, u_2) + dist_squared(v_1, v_2) ) > \
					 ( dist_squared(u_1, v_1) + dist_squared(u_2, v_2) ):
					# is better, put v_1 after u_1, then in reverse order until u_2, then v_2

					# TODO: do in place?
					route_prime = route[:i+1] + list(reversed(route[i+1:j+1])) + route[j+1:]
					return do_route(route_prime, limit-1)

		return route # nothing found
Beispiel #4
0
def get_bonds(atoms):
	bonds = []
	for a in atoms: a.bonded = []
	for i,a in enumerate(atoms):
		for b in atoms[i+1:]:
			d = utils.dist_squared(a,b)**0.5
			if (a.element not in [1,'H'] and b.element not in [1,'H'] and d<2.) or (d < 1.2 and (a.element in [1,'H'])!=(b.element in [1,'H']) ):
				bonds.append( utils.Struct(atoms=(a,b), d=d, e=None) ) #offset from current, distance
				a.bonded.append(b)
				b.bonded.append(a)
	return bonds
Beispiel #5
0
    def do_route(route, limit):  # return new route
        if limit == 0:
            return route
        # don't change depot
        for i in range(0, len(route) - 2):
            u_1 = route[i].pos
            u_2 = route[i + 1].pos
            for j in range(i + 1, len(route) - 1):
                v_1 = route[j].pos
                v_2 = route[j + 1].pos

                if ( dist_squared(u_1, u_2) + dist_squared(v_1, v_2) ) > \
                  ( dist_squared(u_1, v_1) + dist_squared(u_2, v_2) ):
                    # is better, put v_1 after u_1, then in reverse order until u_2, then v_2

                    # TODO: do in place?
                    route_prime = route[:i + 1] + list(
                        reversed(route[i + 1:j + 1])) + route[j + 1:]
                    return do_route(route_prime, limit - 1)

        return route  # nothing found
Beispiel #6
0
def _get_closest_depots(instance, genotype):
	"""Returns the closest depots for the genotype values. Currently unrandomized."""
	raise RuntimeError("don't use anymore")
	closest_depots=[]

	for vehicle_base in genotype:
		#pprint.pprint(list( ( ( (vehicle_base[0]-d.pos[0])**2 + (vehicle_base[1]-d.pos[1])**2 ), d_id) for (d_id, d) in enumerate(instance.depots) ) )

		# use squared dist
		closest = min( (dist_squared(vehicle_base, d.pos), d_id) for (d_id, d) in enumerate(instance.depots) )

		closest_depots.append( instance.depots[ closest[1] ] )

	return closest_depots
Beispiel #7
0
def _get_closest_depots(instance, genotype):
    """Returns the closest depots for the genotype values. Currently unrandomized."""
    raise RuntimeError("don't use anymore")
    closest_depots = []

    for vehicle_base in genotype:
        #pprint.pprint(list( ( ( (vehicle_base[0]-d.pos[0])**2 + (vehicle_base[1]-d.pos[1])**2 ), d_id) for (d_id, d) in enumerate(instance.depots) ) )

        # use squared dist
        closest = min((dist_squared(vehicle_base, d.pos), d_id)
                      for (d_id, d) in enumerate(instance.depots))

        closest_depots.append(instance.depots[closest[1]])

    return closest_depots
Beispiel #8
0
def parse_tinker_arc(molecule_file, parameter_file=None):
	if parameter_file:
		elements, atom_types, bond_types, angle_types, dihedral_types = lammps.parse_opls_parameters(parameter_file)

	atoms = []
	for line in open(molecule_file):
		columns = line.split()
		if len(columns)>3:
			atoms.append( utils.Struct(index=int(columns[0]), element=columns[1], x=float(columns[2]), y=float(columns[3]), z=float(columns[4]), bonded=[int(s) for s in columns[6:]], type=([t for t in atom_types if t.index==int(columns[5][-3:])][0] if parameter_file else None), charge=None) )
			if len(columns[5])>3:
				atom_types.append( copy.deepcopy(atoms[-1].type) )
				atoms[-1].type.index = int(columns[5])
	bond_set = {}
	for a in atoms:
		a.bonded = [atoms[i-1] for i in a.bonded]
		for b in a.bonded:
			if (b,a) not in bond_set:
				bond_set[(a,b)] = True
	bonds = [utils.Struct(atoms=b, d=utils.dist_squared(b[0],b[1])**0.5, e=None, type=None) for b in bond_set.keys()]
	angles, dihedrals = get_angles_and_dihedrals(atoms, bonds)
	
	return atoms, bonds, angles, dihedrals
def build_dot(N, spoc, monomer, atoms, bonds, angles, dihedrals, random_seed=1):
    random.seed(random_seed)
    pb_type = monomer.atoms[0].type
    s_type = monomer.atoms[1].type
    Q = 2.968
    L = int(math.ceil((2 * N) ** 0.333))
    center = utils.Struct(x=0.0, y=0.0, z=0.0)
    core_atoms = []
    if L * Q < 30:  # octahedron
        L += 6
        for zi in range(L):
            # L2 = int(( math.sqrt(3)*( L/2-abs(zi-L/2) ) ))
            L2 = (L / 2 - abs(zi - L / 2)) * 2
            for xi in range(L2):
                for yi in range(L2):
                    x = (xi - L2 * 0.5 + 0.5) * Q
                    y = (yi - L2 * 0.5 + 0.5) * Q
                    z = (zi - L * 0.5 + 0.5) * Q
                    core_atoms.append(
                        utils.Struct(
                            x=x,
                            y=y,
                            z=z,
                            element="Pb" if (xi + yi + zi) % 2 else "S",
                            type=pb_type if (xi + yi + zi) % 2 else s_type,
                        )
                    )
    else:  # cube
        L += 2
        for xi in range(L):
            for yi in range(L):
                for zi in range(L):
                    x = (xi - L * 0.5 + 0.5) * Q
                    y = (yi - L * 0.5 + 0.5) * Q
                    z = (zi - L * 0.5 + 0.5) * Q
                    core_atoms.append(
                        utils.Struct(
                            x=x,
                            y=y,
                            z=z,
                            element="Pb" if (xi + yi + zi) % 2 else "S",
                            type=pb_type if (xi + yi + zi) % 2 else s_type,
                        )
                    )

                # filetypes.write_xyz('out', core_atoms)
                # sys.exit()

    for a in core_atoms:
        a.dist = dist = utils.dist(a, center)
        a.neighbors = []
        for b in core_atoms:
            if a is not b and utils.dist_squared(a, b) < Q ** 2 + 0.1:
                a.neighbors.append(b)

    core_atoms.sort(key=lambda a: a.dist)
    s_atoms = [a for a in core_atoms if a.element == "S"][:N]
    pb_atoms = {}
    for s in s_atoms:
        for a in s.neighbors:
            if a.type is pb_type:
                pb_atoms[a] = True

    pb_atoms = pb_atoms.keys()
    pb_atoms.sort(key=lambda a: a.dist)
    # excess_pb_atoms = pb_atoms[N:] #tends to pick all from one side

    closest_dist_to_remove = pb_atoms[N].dist

    core_pb_atoms = [a for a in pb_atoms if a.dist < closest_dist_to_remove - 0.01]
    marginal_pb_atoms = [
        a for a in pb_atoms if (abs(a.dist - closest_dist_to_remove) < 0.01 and a not in core_pb_atoms)
    ]
    random.shuffle(marginal_pb_atoms)
    core_pb_atoms = core_pb_atoms + marginal_pb_atoms[: N - len(core_pb_atoms)]
    excess_pb_atoms = [a for a in pb_atoms if a not in core_pb_atoms]

    for a in s_atoms + core_pb_atoms:
        atoms.append(a)

    import numpy

    def add_spoc_at_pb(pb):
        spoc.add_to(0.0, 0.0, 0.0, atoms, bonds, angles, dihedrals)

        direction = [pb.x, pb.y, pb.z]
        direction /= numpy.linalg.norm(direction)

        dot = numpy.dot(direction, [1.0, 0.0, 0.0])
        theta = math.acos(dot)
        cross = numpy.cross(direction, [1.0, 0.0, 0.0])
        cross /= -numpy.linalg.norm(cross)
        w = numpy.array(cross)

        for a in atoms[-len(spoc.atoms) :]:
            v = numpy.array([a.x, a.y, a.z])
            a.x, a.y, a.z = (
                v * math.cos(theta) + numpy.cross(w, v) * math.sin(theta) + w * numpy.dot(w, v) * (1 - math.cos(theta))
            )  # Rodrigues' rotation formula
            a.x += pb.x
            a.y += pb.y
            a.z += pb.z

    for pb in excess_pb_atoms:
        add_spoc_at_pb(pb)

        # add more Pb complexes as needed

    new_pb = 0
    while new_pb < N + 3:
        x, y, z = [Q * (3 + (2 * N) ** 0.333) / 2] * 3
        M = utils.rand_rotation()
        x, y, z = utils.matvec(M, [x, y, z])
        pb = utils.Struct(x=x, y=y, z=z, element="Pb", type=pb_type)
        too_close = False
        for a in atoms:
            if utils.dist_squared(a, pb) < (Q + 2) ** 2:
                too_close = True
                break
        if not too_close:
            add_spoc_at_pb(pb)
            new_pb += 1
def radius_of_gyration(atoms):
    center = center_of_geometry(atoms)
    return math.sqrt(1.0 / len(atoms) * sum([utils.dist_squared(a, center) for a in atoms]))
Beispiel #11
0
 def calculate(coords):
     coord_count = 0
     for s in NEB.states[1:-1]:
         for a in s:
             a.x, a.y, a.z = coords[coord_count], coords[
                 coord_count + 1], coords[coord_count + 2]
             coord_count += 3
     #start DFT jobs
     running_jobs = []
     for i, state in enumerate(NEB.states[1:-1]):
         guess = '' if NEB.step == 0 else ' Guess=Read'
         running_jobs.append(
             job('%s-%d-%d' % (NEB.name, NEB.step, i),
                 NEB.theory + ' Force' + guess,
                 state,
                 queue=queue,
                 force=True,
                 previous=('%s-%d-%d' % (NEB.name, NEB.step - 1, i))
                 if NEB.step > 0 else None,
                 extra_section=extra_section))
     #wait for jobs to finish
     for j in running_jobs:
         j.wait()
     #get forces and energies from DFT calculations
     energies = []
     for i, state in enumerate(NEB.states[1:-1]):
         try:
             new_energy, new_atoms = parse_atoms(
                 '%s-%d-%d' % (NEB.name, NEB.step, i))
         except:
             print 'Job failed: %s-%d-%d' % (NEB.name, NEB.step, i)
             exit()
         energies.append(new_energy)
         for a, b in zip(state, new_atoms):
             a.fx = b.fx
             a.fy = b.fy
             a.fz = b.fz
     dft_energies = copy.deepcopy(energies)
     #add spring forces to atoms
     for i, state in enumerate(NEB.states[1:-1]):
         for j, b in enumerate(state):
             a, c = NEB.states[i - 1][j], NEB.states[i + 1][j]
             if j in spring_atoms:
                 b.fx += NEB.k * (a.x - b.x) + NEB.k * (c.x - b.x)
                 b.fy += NEB.k * (a.y - b.y) + NEB.k * (c.y - b.y)
                 b.fz += NEB.k * (a.z - b.z) + NEB.k * (c.z - b.z)
                 energies[i] += 0.5 * NEB.k * (utils.dist_squared(
                     a, b) + utils.dist_squared(b, c))
     #set error
     NEB.error = sum(energies)
     #set forces
     NEB.forces = []
     for state in NEB.states[1:-1]:
         for a in state:
             NEB.forces += [-a.fx, -a.fy,
                            -a.fz]  #derivative of the error
     #increment step
     NEB.step += 1
     #write to xyz file
     NEB.xyz = open(name + '.xyz', 'w')
     for state in NEB.states:
         files.write_xyz(state, NEB.xyz)
     NEB.xyz.close()
     #print data
     print NEB.step, NEB.error, (
         '%10.7g ' * len(dft_energies)) % tuple(dft_energies)