Statistiques
| Révision :

root / ase / io / cif.py

Historique | Voir | Annoter | Télécharger (1,65 ko)

1
from math import sin, cos, pi, sqrt
2
import numpy as np
3

    
4
from ase.atoms import Atoms, Atom
5
from ase.parallel import paropen
6

    
7
"""Module to read and write atoms in cif file format"""
8

    
9

    
10
def read_cif(fileobj, index=-1):
11
    if isinstance(fileobj, str):
12
        fileobj = open(fileobj)
13

    
14
    def search_key(fobj, key):
15
        for line in fobj:
16
            if key in line:
17
                return line
18
        return None
19

    
20
    def get_key(fobj, key, pos=1):
21
        line = search_key(fobj, key)
22
        if line:
23
            return float(line.split()[pos].split('(')[0])
24
        return None
25

    
26
    a = get_key(fileobj, '_cell_length_a')
27
    b = get_key(fileobj, '_cell_length_b')
28
    c = get_key(fileobj, '_cell_length_c')
29
    alpha =  pi * get_key(fileobj, '_cell_angle_alpha') / 180
30
    beta = pi * get_key(fileobj, '_cell_angle_beta') / 180
31
    gamma =  pi * get_key(fileobj, '_cell_angle_gamma') / 180
32

    
33
    va = a * np.array([1, 0, 0])
34
    vb = b * np.array([cos(gamma), sin(gamma), 0])
35
    cx = cos(beta)
36
    cy = (cos(alpha) - cos(beta) * cos(gamma)) / sin(gamma)
37
    cz = sqrt(1. - cx*cx - cy*cy)
38
    vc = c * np.array([cx, cy, cz])
39
    cell = np.array([va, vb, vc])
40

    
41
    atoms = Atoms(cell=cell)
42
    read = False
43
    for line in fileobj:
44
        if not read:
45
            if '_atom_site_disorder_group' in line:
46
                read = True
47
        else:
48
            word = line.split()
49
            if len(word) < 5:
50
                break
51
            symbol = word[1]
52
            pos = (float(word[2].split('(')[0]) * va +
53
                   float(word[3].split('(')[0]) * vb +
54
                   float(word[4].split('(')[0]) * vc   )
55
            atoms.append(Atom(symbol, pos))
56

    
57
    return atoms
58