예제 #1
0
def pbc_distance(s, p1, p2):
    """pysimm.calc.pbc_distance

    Calculates distance between particles using PBC

    Args:
        s: :class:`~pysimm.system.System`
        p1: :class:`~pysimm.system.Particle`
        p2: :class:`~pysimm.system.Particle`
    Returns:
        distance between particles
    """
    if not np:
        raise PysimmError('pysimm.calc.pbc_distance function requires numpy')
    frac_x1 = p1.x / s.dim.dx
    frac_y1 = p1.y / s.dim.dy
    frac_z1 = p1.z / s.dim.dz

    frac_x2 = p2.x / s.dim.dx
    frac_y2 = p2.y / s.dim.dy
    frac_z2 = p2.z / s.dim.dz

    frac_d = np.array([frac_x1 - frac_x2, frac_y1 - frac_y2, frac_z1 - frac_z2])
    frac_d = frac_d - np.round(frac_d)

    dx = frac_d[0] * s.dim.dx
    dy = frac_d[1] * s.dim.dy
    dz = frac_d[2] * s.dim.dz

    return np.linalg.norm([dx, dy, dz])
예제 #2
0
def find_rotation(a, b):
    """pysimm.calc.find_rotation

    Finds rotation vector required to align vector a and vector b

    Args:
        a: 3D vector [x,y,z]
        b: 3D vector [x,y,z]
    Returns:
        rotation matrix
    """
    if not np:
        raise PysimmError('pysimm.calc.find_rotation function requires numpy')
    a = np.array(a)
    b = np.array(b)

    a_x_b = np.cross(a, b)
    axis = a_x_b / np.linalg.norm(a_x_b)

    theta = acos(np.dot(a, b) / np.linalg.norm(a) / np.linalg.norm(b))

    skew = np.matrix([[0, -axis[2], axis[1]],
                     [axis[2], 0, -axis[0]],
                     [-axis[1], axis[0], 0]])

    rot_matrix = np.identity(3) + sin(theta)*skew + (1 - cos(theta))*skew*skew

    return rot_matrix
예제 #3
0
def rotate_vector(x, y, z, theta_x=None, theta_y=None, theta_z=None):
    """pysimm.calc.rotate_vector

    Rotates 3d vector around x-axis, y-axis and z-axis given by user defined angles

    Args:
        x: x vector component
        y: y vector component
        z: z vector component
        theta_x: angle to rotate vector around x axis
        theta_y: angle to rotate vector around y axis
        theta_z: angle to rotate vector around z axis
    Returns:
        new vector [x,y,z]
    """
    if not np:
        raise PysimmError('pysimm.calc.rotate_vector function requires numpy')
    xt = random() * 2 * pi if theta_x is None else theta_x
    yt = random() * 2 * pi if theta_y is None else theta_y
    zt = random() * 2 * pi if theta_z is None else theta_z

    c = np.array((x, y, z))
    rot_mat_x = np.array([[1, 0, 0], [0, cos(xt), -sin(xt)],
                          [0, sin(xt), cos(xt)]])
    rot_mat_y = np.array([[cos(yt), 0, sin(yt)], [0, 1, 0],
                          [-sin(yt), 0, cos(yt)]])
    rot_mat_z = np.array([[cos(zt), -sin(zt), 0], [sin(zt),
                                                   cos(zt), 0], [0, 0, 1]])

    return list(np.dot(rot_mat_z, np.dot(rot_mat_y, np.dot(rot_mat_x, c))))
예제 #4
0
def chiral_angle(a, b, c, d):
    """pysimm.calc.chiral_angle

    Finds chiral angle between four pysimm.system.Particle objects

    Args:
        a: pysimm.system.Particle
        b: pysimm.system.Particle
        c: pysimm.system.Particle
        d: pysimm.system.Particle
    Returns:
        chiral angle for particles
    """
    if not np:
        raise PysimmError('pysimm.calc.chiral_angle function requires numpy')
    ht = np.array([a.x - b.x, a.y - b.y, a.z - b.z])
    ht /= np.linalg.norm(ht)

    hmethyl = np.array([a.x - d.x, a.y - d.y, a.z - d.z])
    hmethyl /= np.linalg.norm(hmethyl)

    hside = np.array([a.x - c.x, a.y - c.y, a.z - c.z])
    hside /= np.linalg.norm(hside)

    side_x_methyl = np.cross(hside, hmethyl)

    side_dot_methyl = np.dot(hside, hmethyl)
    side_theta_methyl = acos(side_dot_methyl)

    side_x_methyl /= sin(side_theta_methyl)

    cos_theta = np.dot(side_x_methyl, ht)

    return acos(cos_theta) / pi * 180
예제 #5
0
def rotate_vector(x, y, z, theta_x=None, theta_y=None, theta_z=None):
    """pysimm.calc.rotate_vector

    Rotates vector

    Args:
        x: x vector component
        y: y vector component
        z: z vector component
        theta_x: angle to rotate vector around x axis
        theta_y: angle to rotate vector around y axis
        theta_z: angle to rotate vector around z axis
    Returns:
        new vector [x,y,z]
    """
    if not np:
        raise PysimmError('pysimm.calc.rotate_vector function requires numpy')
    xt = random() * 2 * pi if theta_x is None else theta_x
    yt = random() * 2 * pi if theta_y is None else theta_y
    zt = random() * 2 * pi if theta_z is None else theta_z

    c = np.matrix([[x], [y], [z]])

    rot_mat_x = np.matrix([[1, 0, 0], [0, cos(xt), -sin(xt)],
                           [0, sin(xt), cos(xt)]])
    rot_mat_y = np.matrix([[cos(yt), 0, sin(yt)], [0, 1, 0],
                           [-sin(yt), 0, cos(yt)]])
    rot_mat_z = np.matrix([[cos(zt), -sin(zt), 0], [sin(zt),
                                                    cos(zt), 0], [0, 0, 1]])

    c = rot_mat_x * c
    c = rot_mat_y * c
    c = rot_mat_z * c

    return [x[0] for x in c.tolist()]
예제 #6
0
def rot_hyperbola(x, a, b, c, d, e, th):
    if not np:
        raise PysimmError('pysimm.calc.rot_hyperbola function requires numpy')
    pars = a, b, c, 0, 0  # do the shifting after rotation
    xd = x - d
    hsin = hyperbola(xd, *pars) * np.sin(th)
    xcos = xd * np.cos(th)
    return e + hyperbola(xcos - hsin, *pars) * np.cos(th) + xcos - hsin
예제 #7
0
def hyperbola(x, a, b, c, d, e):
    if not np:
        raise PysimmError('pysimm.calc.hyperbola function requires numpy')
    #   hyperbola(x) with parameters
    #   a/b = asymptotic slope
    #    c  = curvature at vertex
    #    d  = offset to vertex
    #    e  = vertical offset
    return a * np.sqrt((b * c)**2 + (x - d)**2) / b + e
예제 #8
0
def distance(p1, p2):
    """pysimm.calc.distance

    Finds distance between two :class:`~pysimm.system.Particle` objects. Simply calculates length of vector between particle coordinates and does not consider periodic boundary conditions.

    Args:
        p1: :class:`~pysimm.system.Particle`
        p2: :class:`~pysimm.system.Particle`
    Returns:
        distance between particles
    """
    if not np:
        raise PysimmError('pysimm.calc.distance function requires numpy')
    return np.linalg.norm([p1.x - p2.x, p1.y - p2.y, p1.z - p2.z])
예제 #9
0
def distance(p1, p2):
    """pysimm.calc.distance

    Finds distance between two pysimm.system.Particle objects

    Args:
        p1: pysimm.system.Particle
        p2: pysimm.system.Particle
    Returns:
        distance between particles
    """
    if not np:
        raise PysimmError('pysimm.calc.distance function requires numpy')
    return np.linalg.norm([p1.x - p2.x, p1.y - p2.y, p1.z - p2.z])
예제 #10
0
파일: calc.py 프로젝트: jrdcasa/pysimm
def rotate_vector(x, y, z, theta_x=None, theta_y=None, theta_z=None):
    """pysimm.calc.rotate_vector

    Rotates 3d vector around x-axis, y-axis and z-axis given by user defined angles

    Args:
        x: x vector component
        y: y vector component
        z: z vector component
        theta_x: angle to rotate vector around x axis
        theta_y: angle to rotate vector around y axis
        theta_z: angle to rotate vector around z axis
    Returns:
        new vector [x,y,z]
    """
    if not np:
        raise PysimmError('pysimm.calc.rotate_vector function requires numpy')
    xt = random() * 2 * pi if theta_x is None else theta_x
    yt = random() * 2 * pi if theta_y is None else theta_y
    zt = random() * 2 * pi if theta_z is None else theta_z

    #cJ PendingDeprecationWarning: the matrix subclass
    c = np.array([[x], [y], [z]])

    rot_mat_x = np.array([[1, 0, 0],
                           [0, cos(xt), -sin(xt)],
                           [0, sin(xt), cos(xt)]])
    rot_mat_y = np.array([[cos(yt), 0, sin(yt)],
                           [0, 1, 0],
                           [-sin(yt), 0, cos(yt)]])
    rot_mat_z = np.array([[cos(zt), -sin(zt), 0],
                           [sin(zt), cos(zt), 0],
                           [0, 0, 1]])

    c = np.dot(rot_mat_x, c)
    c = np.dot(rot_mat_y, c)
    c = np.dot(rot_mat_z, c)

    return [x[0] for x in c.tolist()]
예제 #11
0
def chiral_angle(a, b, c, d):
    """pysimm.calc.chiral_angle

    Finds chiral angle between four :class:`~pysimm.system.Particle` objects. Chiral angle is defined as the angle between the vector resulting from vec(a->c) X vec(a->d) and vec(a->b). Used to help define tacticity where backbone follow b'--a--b and c and d are side groups.
           
       b'--a--b
          / \
         c   d
    
    Args:
        a: pysimm.system.Particle
        b: pysimm.system.Particle
        c: pysimm.system.Particle
        d: pysimm.system.Particle
    Returns:
        chiral angle
    """
    if not np:
        raise PysimmError('pysimm.calc.chiral_angle function requires numpy')
    ht = np.array([a.x-b.x, a.y-b.y, a.z-b.z])
    ht /= np.linalg.norm(ht)

    hmethyl = np.array([a.x-d.x, a.y-d.y, a.z-d.z])
    hmethyl /= np.linalg.norm(hmethyl)

    hside = np.array([a.x-c.x, a.y-c.y, a.z-c.z])
    hside /= np.linalg.norm(hside)

    side_x_methyl = np.cross(hside, hmethyl)

    side_dot_methyl = np.dot(hside, hmethyl)
    side_theta_methyl = acos(side_dot_methyl)

    side_x_methyl /= sin(side_theta_methyl)

    cos_theta = np.dot(side_x_methyl, ht)

    return acos(cos_theta)/pi*180
예제 #12
0
def tacticity(s, a_tag=None, b_tag=None, c_tag=None, d_tag=None, offset=None, return_angles=True, unwrap=True,
              rewrap=True, skip_first=False):
    """pysimm.calc.tacticity

    Determines tacticity for polymer chain. Iterates through groups of four patricles given by X_tags, using offset. This assumes equivalent atoms in each group of four are perfectly offset.

    Args:
        s: :class:`~pysimm.system.System`
        a_tag: tag of first a particle
        b_tag: tag of first b particle
        c_tag: tag of first c particle
        d_tag: tag of first d particle
        offset: offset of particle tags (monomer repeat atomic count)
        return_angles: if True return chiral angles of all monomers
        unwrap: True to perform unwrap before calculation (REQUIRED before calculation, but not required in this
        function)
        rewrap: True to rewrap system after calculation
        skip_first: True to skip first monomer (sometime chirality is poorly defined for thsi monomer)
    Returns:
        tacticity or tacticity, [chiral_angles]
    """
    if not np:
        raise PysimmError('pysimm.calc.tacticity function requires numpy')
    if a_tag is None or b_tag is None or c_tag is None or d_tag is None:
        error_print('particle tags for chiral center are required')
        error_print('a: chiral center, b-d: 3 side groups')

    if offset is None:
        error_print('offset for tags in each monomer is required, i.e. - number of particles in each monomer')

    if unwrap:
        s.unwrap()

    a_ = [s.particles[i] for i in range(a_tag, s.particles.count, offset)]
    b_ = [s.particles[i] for i in range(b_tag, s.particles.count, offset)]
    c_ = [s.particles[i] for i in range(c_tag, s.particles.count, offset)]
    d_ = [s.particles[i] for i in range(d_tag, s.particles.count, offset)]

    stereochem_angles = []

    if skip_first:
        for a, b, c, d in izip(a_[1:], b_[1:], c_[1:], d_[1:]):
            stereochem_angles.append(chiral_angle(a, b, c, d))
    else:
        for a, b, c, d in izip(a_, b_, c_, d_):
            stereochem_angles.append(chiral_angle(a, b, c, d))

    last = None
    iso_diads = 0
    syn_diads = 0
    for a in stereochem_angles:
        if last is not None:
            if (a < 90 and last < 90) or (a > 90 and last > 90):
                iso_diads += 1
            else:
                syn_diads += 1
        last = a

    if iso_diads == (len(stereochem_angles) - 1):
        t = 'isotactic'
    elif syn_diads == (len(stereochem_angles) - 1):
        t = 'syndiotactic'
    else:
        t = 'atactic'

    if rewrap:
        s.wrap()

    print('{:.1f}% syn diads'.format(100*float(syn_diads)/(syn_diads+iso_diads)))
    print('{:.1f}% iso diads'.format(100*float(iso_diads)/(syn_diads+iso_diads)))
    if return_angles:
        return t, stereochem_angles
    else:
        return t
예제 #13
0
def call_lammps(simulation, np, nanohub):
    """pysimm.lmps.call_lammps

    Wrapper to call LAMMPS using executable name defined in pysimm.lmps module.

    Args:
        simulation: pysimm.lmps.Simulation object reference
        np: number of threads to use
        nanohub: dictionary containing nanohub resource information default=None

    Returns:
        None
    """
    if nanohub:
        if simulation.name:
            print('%s: sending %s simulation to computer cluster at nanoHUB' % (strftime('%H:%M:%S'), simulation.name))
        sys.stdout.flush()
        cmd = ('submit -n %s -w %s -i temp.lmps -i temp.in '
               'lammps-09Dec14-parallel -e both -l none -i temp.in'
               % (nanohub.get('cores'), nanohub.get('walltime')))
        cmd = shlex.split(cmd)
        exit_status, stdo, stde = RapptureExec(cmd)
    else:
        if simulation.name:
            print('%s: starting %s simulation using LAMMPS'
                  % (strftime('%H:%M:%S'), simulation.name))
        else:
            print('%s: starting simulation using LAMMPS'
                  % strftime('%H:%M:%S'))
        if np:
            p = Popen(['mpiexec', '-np', str(np),
                       LAMMPS_EXEC, '-e', 'both', '-l', 'none'],
                      stdin=PIPE, stdout=PIPE, stderr=PIPE)
        else:
            p = Popen(['mpiexec', LAMMPS_EXEC, '-e', 'both', '-l', 'none'],
                      stdin=PIPE, stdout=PIPE, stderr=PIPE)
        simulation.write_input()
        p.stdin.write(simulation.input)
        q = Queue()
        t = Thread(target=enqueue_output, args=(p.stdout, q))
        t.daemon = True
        t.start()

        while t.isAlive() or not q.empty():
            try:
                line = q.get_nowait()
            except Empty:
                pass
            else:
                if simulation.print_to_screen:
                    sys.stdout.write(line)
                    sys.stdout.flush()
                    
    simulation.system.read_lammps_dump('pysimm.dump.tmp')
    '''if simulation.write:
        n = read_lammps(simulation.write, quiet=True,
                        pair_style=simulation.system.pair_style,
                        bond_style=simulation.system.bond_style,
                        angle_style=simulation.system.angle_style,
                        dihedral_style=simulation.system.dihedral_style,
                        improper_style=simulation.system.improper_style)
    else:
        n = read_lammps('pysimm_md.lmps', quiet=True,
                        pair_style=simulation.system.pair_style,
                        bond_style=simulation.system.bond_style,
                        angle_style=simulation.system.angle_style,
                        dihedral_style=simulation.system.dihedral_style,
                        improper_style=simulation.system.improper_style)
    for p in n.particles:
        p_ = simulation.system.particles[p.tag]
        p_.x = p.x
        p_.y = p.y
        p_.z = p.z
        p_.vx = p.vx
        p_.vy = p.vy
        p_.vz = p.vz
    simulation.system.dim = n.dim'''

    try:
        os.remove('temp.lmps')
    except OSError as e:
        print e
        
    if os.path.isfile('pysimm.qeq.tmp'):
        os.remove('pysimm.qeq.tmp')
        
    try:
        os.remove('pysimm.dump.tmp')
        if simulation.name:
            print('%s: %s simulation using LAMMPS successful'
                  % (strftime('%H:%M:%S'), simulation.name))
        else:
            print('%s: molecular dynamics using LAMMPS successful'
                  % (strftime('%H:%M:%S')))
    except OSError as e:
        if simulation.name:
            raise PysimmError('%s simulation using LAMMPS UNsuccessful' % simulation.name)
        else:
            raise PysimmError('molecular dynamics using LAMMPS UNsuccessful')

    '''if not simulation.write: