Example #1
0
    def test_read_cif():
        """
        Read La2CuO4 structure from a CIF file.
        """
        from structure import read_structure, generate_structure

        files = get_files()

        # Read from CIF file
        s = read_structure(files['La2CuO4_ICSD69312.cif'])

        ref = generate_structure(
            units='A',
            axes=[[2.665, 0., -6.5525], [0., 5.4126, 0.], [2.665, 0., 6.5525]],
            elem='La La La La Cu Cu O O O O O O O O'.split(),
            pos=[[2.665, 5.37038172,
                  -1.8071795], [2.665, 2.74851828, 4.7453205],
                 [2.665, 2.66408172, -4.7453205],
                 [2.665, 0.04221828, 1.8071795], [0., 0., 0.],
                 [2.665, 2.7063, 0.], [1.3325, 1.35315, -0.128429],
                 [3.9975, 4.05945, 0.128429], [3.9975, 1.35315, -0.128429],
                 [1.3325, 4.05945, 0.128429], [2.665, 0.23490684, -4.1398695],
                 [2.665, 2.47139316,
                  2.4126305], [2.665, 2.94120684, -2.4126305],
                 [2.665, 5.17769316, 4.1398695]],
        )

        assert (structure_same(s, ref))
Example #2
0
def test_bounding_box():
    import numpy as np
    from structure import generate_structure, read_structure

    files = get_files()

    h2o = generate_structure(
        elem=['O', 'H', 'H'],
        pos=[[0.000000, 0.000000, 0.000000], [0.000000, -0.757160, 0.586260],
             [0.000000, 0.757160, 0.586260]],
        units='A',  # Angstroms
    )

    # add a box by hand to the water molecule
    h2o_diy = h2o.copy()
    h2o_diy.set_axes(8.0 * np.eye(3))
    assert (value_eq(h2o_diy.axes, 8. * np.eye(3)))

    # automatically add a bounding box to the water molecule
    h2o_auto = h2o.copy()
    h2o_auto.bounding_box(box='cubic', minsize=8.0)
    assert (value_eq(h2o_auto.axes, 8. * np.eye(3)))
    assert (value_eq(tuple(h2o_auto.pos[-1]), (4., 4.75716, 4.29313)))

    s = read_structure(files['coronene.xyz'])

    # make a bounding box that is at least 5 A from the nearest atom
    s.bounding_box(mindist=5.0)

    ref_axes = np.array([[16.4035, 0., 0.], [0., 16.3786, 0.], [0., 0., 10.]])

    assert (value_eq(s.axes, ref_axes))
    assert (value_eq(s.pos[:, 2].min(), 5.0))
    assert (value_eq(s.pos[:, 2].max(), 5.0))
Example #3
0
def test_read_write():
    """
    Write/read conventional diamond cell to/from XYZ, XSF, and POSCAR formats.
    """
    import os
    from structure import generate_structure, read_structure

    tpath = testing.setup_unit_test_output_directory('structure',
                                                     'test_read_write')

    d8 = generate_structure(
        structure='diamond',
        cell='conv',
    )

    # Write an XYZ file
    xyz_file = os.path.join(tpath, 'diamond8.xyz')
    d8.write(xyz_file)

    # Write an XSF file
    xsf_file = os.path.join(tpath, 'diamond8.xsf')
    d8.write(xsf_file)

    # Write a POSCAR file
    poscar_file = os.path.join(tpath, 'diamond8.POSCAR')
    d8.write(poscar_file)

    # Read an XYZ file
    d8_xyz = read_structure(xyz_file)  # no cell info
    assert (value_eq(d8_xyz.elem, d8.elem))
    assert (value_eq(d8_xyz.pos, d8.pos))

    # Read an XSF file
    d8_xsf = read_structure(xsf_file)
    assert (structure_same(d8_xsf, d8))

    # Read a POSCAR file
    d8_poscar = read_structure(poscar_file)

    assert (structure_same(d8_poscar, d8))
Example #4
0
def demo_read_cif():
    """
    Read La2CuO4 structure from a CIF file.
    """

    # Note: this demo requires PyCifRW

    # Read from CIF file
    s = read_structure('La2CuO4_ICSD69312.cif')

    # Print out the structure
    print('La2CuO4 in POSCAR format:')
    print(s.write_poscar())
Example #5
0
def demo_read():
    """
    Read conventional diamond cell from XYZ, XSF, and POSCAR formats.
    """

    # Read an XYZ file
    d8_xyz = read_structure('diamond8.xyz')  # no cell info

    # Read an XSF file
    d8_xsf = read_structure('diamond8.xsf')

    # Read a POSCAR file
    d8_poscar = read_structure('diamond8.POSCAR')

    # Compare with the reference structure
    d8 = generate_structure(
        structure='diamond',
        cell='conv',
    )

    def struct_same(s1, s2, axes=True):
        same = True
        same &= value_eq(s1.elem, s2.elem)
        same &= value_eq(s1.pos, s2.pos)
        if axes:
            same &= value_eq(s1.axes, s2.axes)
        #end if
        return same

    #end def struct_same

    print('\nXYZ valid? {}'.format(struct_same(d8_xyz, d8, axes=False)))

    print('\nXSF valid? {}'.format(struct_same(d8_xsf, d8)))

    print('\nPOSCAR valid? {}'.format(struct_same(d8_poscar, d8)))
Example #6
0
def demo_coronene_box():
    """
    Place coronene in a well apportioned box.
    """

    s = read_structure('./coronene.xyz')

    # make a bounding box that is at least 5 A from the nearest atom
    s.bounding_box(mindist=5.0)

    # print the resulting box
    print(s.axes)

    # plot the coronene molecule with an automatic box
    plt.figure(tight_layout=True)
    s.plot2d_ax(0, 1, 'k', lw=2)
    s.plot2d_pos(0, 1, 'bo')
    plt.axis('equal')
    plt.xlabel('x (A)')
    plt.ylabel('y (A)')
    plt.title('demo coronene box: box with minimum distance')
    plt.show()
Example #7
0
def generate_physical_system(**kwargs):
    for var, val in ps_defaults.items():
        if not var in kwargs:
            kwargs[var] = val
        #end if
    #end for
    type = kwargs['type']
    if type == 'atom' or type == 'dimer' or type == 'trimer':
        del kwargs['kshift']
        del kwargs['tiling']
        #if not 'units' in kwargs:
        #    kwargs['units'] = 'B'
        ##end if
        tiling = None
    else:
        tiling = kwargs['tiling']
    #end if

    if 'structure' in kwargs:
        s = kwargs['structure']
        is_str = isinstance(s, str)
        if is_str:
            if os.path.exists(s):
                if 'elem' in kwargs:
                    s = read_structure(s, elem=kwargs['elem'])
                else:
                    s = read_structure(s)
                #end if
                if 'axes' in kwargs:
                    s.reset_axes(kwargs['axes'])
                #end if
                kwargs['structure'] = s
            else:
                slow = s.lower()
                format = None
                if '.' in slow:
                    format = slow.rsplit('.')[1]
                elif 'poscar' in slow:
                    format = 'poscar'
                #end if
                is_path = '/' in s
                is_file = format in set('xyz xsf poscar cif fhi-aims'.split())
                if is_path or is_file:
                    PhysicalSystem.class_error(
                        'user provided structure file does not exist\nstructure file path: '
                        + s, 'generate_physical_system')
                #end if
            #end if
        #end if
    #end if

    generation_info = obj()
    generation_info.transfer_from(deepcopy(kwargs))

    net_charge = kwargs['net_charge']
    net_spin = kwargs['net_spin']
    tiled_spin = kwargs['tiled_spin']
    extensive = kwargs['extensive']
    del kwargs['net_spin']
    del kwargs['net_charge']
    del kwargs['tiled_spin']
    del kwargs['extensive']
    if 'particles' in kwargs:
        particles = kwargs['particles']
        del kwargs['particles']
    else:
        generation_info.particles = None
    #end if
    pretile = kwargs['pretile']
    del kwargs['pretile']
    valency = dict()
    remove = []
    for var in kwargs:
        #if var in Matter.elements:
        if is_element(var):
            valency[var] = kwargs[var]
            remove.append(var)
        #end if
    #end if
    generation_info.valency = deepcopy(valency)
    for var in remove:
        del kwargs[var]
    #end for

    if pretile is None:
        structure = generate_structure(**kwargs)
    else:
        for d in range(len(pretile)):
            if tiling[d] % pretile[d] != 0:
                PhysicalSystem.class_error(
                    'pretile does not divide evenly into tiling\n  tiling provided: {0}\n  pretile provided: {1}'
                    .format(tiling, pretile), 'generate_physical_system')
            #end if
        #end for
        tiling = tuple(array(tiling) // array(pretile))
        kwargs['tiling'] = pretile
        pre = generate_structure(**kwargs)
        pre.remove_folded_structure()
        structure = pre.tile(tiling)
    #end if

    if tiling != None and tiling != (1, 1, 1) and structure.has_folded():
        fps = PhysicalSystem(structure=structure.folded_structure,
                             net_charge=net_charge,
                             net_spin=net_spin,
                             **valency)
        structure.remove_folded()
        folded_structure = fps.structure
        if extensive:
            ncells = int(round(structure.volume() / folded_structure.volume()))
            net_charge = ncells * net_charge
            if not isinstance(net_spin, str):
                net_spin = ncells * net_spin
            #end if
        #end if
        if tiled_spin != None:
            net_spin = tiled_spin
        #end if
        ps = PhysicalSystem(structure=structure,
                            net_charge=net_charge,
                            net_spin=net_spin,
                            **valency)
        structure.set_folded(folded_structure)
        ps.folded_system = fps
    else:
        ps = PhysicalSystem(structure=structure,
                            net_charge=net_charge,
                            net_spin=net_spin,
                            **valency)
    #end if

    ps.generation_info = generation_info

    return ps
Example #8
0
def generate_physical_system(**kwargs):
    for var,val in ps_defaults.iteritems():
        if not var in kwargs:
            kwargs[var] = val
        #end if
    #end for
    type = kwargs['type']
    if type=='atom' or type=='dimer' or type=='trimer':
        del kwargs['kshift']
        del kwargs['tiling']
        #if not 'units' in kwargs:
        #    kwargs['units'] = 'B'
        ##end if
        tiling = None
    else:
        tiling = kwargs['tiling']
    #end if

    if 'structure' in kwargs:
        s = kwargs['structure']
        is_str = isinstance(s,str)
        if is_str and os.path.exists(s):# and '.' in os.path.split(s)[1]:
            if 'elem' in kwargs:
                print 'system using elem'
                kwargs['structure'] = read_structure(s,elem=kwargs['elem'])
            else:
                kwargs['structure'] = read_structure(s)
            #end if
        elif is_str and '/' in s:
            PhysicalSystem.class_error('path provided for structure file does not exist: '+s,'generate_physical_system')
        #end if
    #end if

    generation_info = obj()
    generation_info.transfer_from(deepcopy(kwargs))

    net_charge = kwargs['net_charge']
    net_spin   = kwargs['net_spin']
    tiled_spin = kwargs['tiled_spin']
    extensive  = kwargs['extensive']
    del kwargs['net_spin']
    del kwargs['net_charge']
    del kwargs['tiled_spin']
    del kwargs['extensive']
    if 'particles' in kwargs:
        particles = kwargs['particles']
        del kwargs['particles']
    else:
        generation_info.particles = None
    #end if
    pretile = kwargs['pretile']
    del kwargs['pretile']
    valency = dict()
    remove = []
    for var in kwargs:
        #if var in Matter.elements:
        if is_element(var):     
            valency[var] = kwargs[var]
            remove.append(var)
        #end if
    #end if
    generation_info.valency = deepcopy(valency)
    for var in remove:
        del kwargs[var]
    #end for

    if pretile is None:
        structure = generate_structure(**kwargs)
    else:
        for d in range(len(pretile)):
            if tiling[d]%pretile[d]!=0:
                PhysicalSystem.class_error('pretile does not divide evenly into tiling\n  tiling provided: {0}\n  pretile provided: {1}'.format(tiling,pretile),'generate_physical_system')
            #end if
        #end for
        tiling = tuple(array(tiling)/array(pretile))
        kwargs['tiling'] = pretile
        pre = generate_structure(**kwargs)
        pre.remove_folded_structure()
        structure = pre.tile(tiling)
    #end if

    if tiling!=None and tiling!=(1,1,1):
        fps = PhysicalSystem(
            structure  = structure.folded_structure,
            net_charge = net_charge,
            net_spin   = net_spin,
            **valency
            )
        structure.remove_folded()
        folded_structure = fps.structure
        if extensive:
            ncells = int(round(structure.volume()/folded_structure.volume()))
            net_charge = ncells*net_charge
            net_spin   = ncells*net_spin
        #end if
        if tiled_spin!=None:
            net_spin = tiled_spin
        #end if
        ps = PhysicalSystem(
            structure  = structure,
            net_charge = net_charge,
            net_spin   = net_spin,
            **valency
            )
        structure.set_folded(folded_structure)
        ps.folded_system = fps
    else:
        ps = PhysicalSystem(
            structure  = structure,
            net_charge = net_charge,
            net_spin   = net_spin,
            **valency
            )
    #end if
    
    ps.generation_info = generation_info

    return ps
Example #9
0
def test_input():
    # imports
    import os
    import numpy as np
    import pwscf_input as pwi
    from generic import obj
    from structure import read_structure
    from physical_system import generate_physical_system
    from pwscf_input import check_new_variables,check_section_classes
    from pwscf_input import PwscfInput,generate_pwscf_input
 
    # directories
    tpath = testing.setup_unit_test_output_directory('pwscf_input','test_input')

    # files
    files = get_files()

    # divert logging function
    divert_nexus_log()

    # definitions
    def check_pw_same(pw1_,pw2_,l1='pw1',l2='pw2'):
        pw_same = object_eq(pw1_,pw2_,int_as_float=True)
        if not pw_same:
            d,d1,d2 = object_diff(pw1_,pw2_,full=True,int_as_float=True)
            diff = obj({l1:obj(d1),l2:obj(d2)})
            failed(str(diff))
        #end if
    #end def check_pw_same


    # test internal spec
    check_new_variables(exit=False)
    check_section_classes(exit=False)


    # test compose
    compositions = obj()

    # based on sample_inputs/Fe_start_ns_eig.in
    pw = PwscfInput()
    pw.control.set(
        calculation   = 'scf' ,
        restart_mode  = 'from_scratch' ,
        wf_collect    = True ,
        outdir        = './output' ,
        pseudo_dir    = '../pseudo/' ,
        prefix        = 'fe' ,
        etot_conv_thr = 1.0e-9 ,
        forc_conv_thr = 1.0e-6 ,
        tstress       = True ,
        tprnfor       = True ,
        )
    pw.system.set(
        ibrav           = 1,
        nat             = 2,
        ntyp            = 1,
        ecutwfc         = 100 ,
        ecutrho         = 300 ,
        nbnd            = 18,
        occupations     = 'smearing',
        degauss         = 0.0005 ,
        smearing        = 'methfessel-paxton' ,
        nspin           = 2 ,
        assume_isolated = 'martyna-tuckerman',
        lda_plus_u      = True ,
        )
    pw.system.set({
        'celldm(1)' : 15,
        'starting_magnetization(1)' : 0.9,
        'hubbard_u(1)' : 3.1,
        'starting_ns_eigenvalue(1,2,1)' : 0.0,
        'starting_ns_eigenvalue(2,2,1)' : 0.0476060,
        'starting_ns_eigenvalue(3,2,1)' : 0.0476060,
        'starting_ns_eigenvalue(4,2,1)' : 0.9654373,
        'starting_ns_eigenvalue(5,2,1)' : 0.9954307,
        })
    pw.electrons.set(
        conv_thr        = 1.0e-9 ,
        mixing_beta     = 0.7 ,
        diagonalization = 'david' ,
        mixing_fixed_ns = 500,
        )
    pw.atomic_species.set(
        atoms            = ['Fe'],
        masses           = obj(Fe=58.69000),
        pseudopotentials = obj(Fe='Fe.pbe-nd-rrkjus.UPF'),
        )
    pw.atomic_positions.set(
        specifier = 'angstrom',
        atoms     = ['Fe','Fe'],
        positions = np.array([
            [2.070000000,   0.000000000,   0.000000000],   
            [0.000000000,   0.000000000,   0.000000000], 
            ]),
        )
    pw.k_points.set(
        specifier = 'automatic',
        grid      = np.array((1,1,1)),
        shift     = np.array((1,1,1)),
        )

    compositions['Fe_start_ns_eig.in'] = pw


    # test read
    pwr = PwscfInput(files['Fe_start_ns_eig.in'])
    pwc = pw.copy()
    pwc.standardize_types()
    check_pw_same(pwc,pwr,'compose','read')


    # test write
    infile = os.path.join(tpath,'pwscf.in')
    pw.write(infile)
    pw2 = PwscfInput()
    pw2.read(infile)
    check_pw_same(pw2,pwr)


    # test read/write/read
    reads = obj()
    for infile in input_files:
        read_path = files[infile]
        write_path = os.path.join(tpath,infile)
        if os.path.exists(write_path):
            os.remove(write_path)
        #end if
        pw = PwscfInput(read_path)
        pw.write(write_path)
        pw2 = PwscfInput(write_path)
        check_pw_same(pw,pw2,'read','write/read')
        reads[infile] = pw
    #end for


    # test generate
    generations = obj()

    # based on sample_inputs/VO2_M1_afm.in
    infile      = 'VO2_M1_afm.in'
    struct_file = files['VO2_M1_afm.xsf']
    read_path   = files[infile]
    write_path  = os.path.join(tpath,infile)

    s = read_structure(struct_file)
    s.elem[0] = 'V1'
    s.elem[1] = 'V2'
    s.elem[2] = 'V1'
    s.elem[3] = 'V2'

    vo2 = generate_physical_system(
        structure = s,
        V1        = 13,
        V2        = 13,
        O         =  6,
        )

    pw = generate_pwscf_input(
        selector         = 'generic',
        calculation      = 'scf',
        disk_io          = 'low',
        verbosity        = 'high',
        wf_collect       = True,
        input_dft        = 'lda',
        hubbard_u        = obj(V1=3.5,V2=3.5),
        ecutwfc          = 350,
        bandfac          = 1.3,
        nosym            = True,
        occupations      = 'smearing',
        smearing         = 'fermi-dirac',
        degauss          = 0.0001,
        nspin            = 2,
        start_mag        = obj(V1=1.0,V2=-1.0),
        diagonalization  = 'david',
        conv_thr         = 1e-8,
        mixing_beta      = 0.2,
        electron_maxstep = 1000,
        system           = vo2,
        pseudos          = ['V.opt.upf','O.opt.upf'],
        kgrid            = (6,6,6),
        kshift           = (0,0,0),
        # added for reverse compatibility
        celldm           = {1:1.0},
        cell_option      = 'alat',
        positions_option = 'alat',
        )

    generations[infile] = pw

    if os.path.exists(write_path):
        os.remove(write_path)
    #end if
    pw.write(write_path)
    pw2 = PwscfInput(read_path)
    pw3 = PwscfInput(write_path)
    check_pw_same(pw2,pw3,'generate','read')

    # based on sample_inputs/Fe_start_ns_eig.in
    infile     = 'Fe_start_ns_eig.in'
    read_path  = files[infile]
    write_path = os.path.join(tpath,infile)

    pw = generate_pwscf_input(
        selector        = 'generic',
        calculation     = 'scf',
        restart_mode    = 'from_scratch',
        wf_collect      = True,
        outdir          = './output',
        pseudo_dir      = '../pseudo/',
        prefix          = 'fe',
        etot_conv_thr   = 1.0e-9,
        forc_conv_thr   = 1.0e-6,
        tstress         = True,
        tprnfor         = True,
        ibrav           = 1,
        nat             = 2,
        ntyp            = 1,
        ecutwfc         = 100,
        ecutrho         = 300,
        nbnd            = 18,
        occupations     = 'smearing',
        degauss         = 0.0005,
        smearing        = 'methfessel-paxton',
        nspin           = 2,
        assume_isolated = 'martyna-tuckerman',
        lda_plus_u      = True,
        conv_thr        = 1.0e-9,
        mixing_beta     = 0.7,
        diagonalization = 'david',
        mixing_fixed_ns = 500,
        mass            = obj(Fe=58.69000),
        pseudos         = ['Fe.pbe-nd-rrkjus.UPF'],
        elem            = ['Fe','Fe'],
        pos             = [[2.070000000, 0.000000000, 0.000000000],    
                           [0.000000000, 0.000000000, 0.000000000]],
        pos_specifier   = 'angstrom',
        kgrid           = np.array((1,1,1)),
        kshift          = np.array((1,1,1)),
        )
    pw.system.set({
        'celldm(1)' : 15,
        'starting_magnetization(1)' : 0.9,
        'hubbard_u(1)' : 3.1,
        'starting_ns_eigenvalue(1,2,1)' : 0.0,
        'starting_ns_eigenvalue(2,2,1)' : 0.0476060,
        'starting_ns_eigenvalue(3,2,1)' : 0.0476060,
        'starting_ns_eigenvalue(4,2,1)' : 0.9654373,
        'starting_ns_eigenvalue(5,2,1)' : 0.9954307,
        })

    generations[infile] = pw

    pw2 = compositions[infile]
    check_pw_same(pw,pw2,'generate','compose')
    if os.path.exists(write_path):
        os.remove(write_path)
    #end if
    pw.write(write_path)
    pw3 = PwscfInput(write_path)
    pw4 = reads[infile]
    check_pw_same(pw3,pw4,'generate','read')



    # based on sample_inputs/Fe_start_ns_eig.in
    #  variant that uses direct pwscf array input
    pw = generate_pwscf_input(
        selector        = 'generic',
        calculation     = 'scf',
        restart_mode    = 'from_scratch',
        wf_collect      = True,
        outdir          = './output',
        pseudo_dir      = '../pseudo/',
        prefix          = 'fe',
        etot_conv_thr   = 1.0e-9,
        forc_conv_thr   = 1.0e-6,
        tstress         = True,
        tprnfor         = True,
        ibrav           = 1,
        nat             = 2,
        ntyp            = 1,
        ecutwfc         = 100,
        ecutrho         = 300,
        nbnd            = 18,
        occupations     = 'smearing',
        degauss         = 0.0005,
        smearing        = 'methfessel-paxton',
        nspin           = 2,
        assume_isolated = 'martyna-tuckerman',
        lda_plus_u      = True,
        conv_thr        = 1.0e-9,
        mixing_beta     = 0.7,
        diagonalization = 'david',
        mixing_fixed_ns = 500,
        mass            = obj(Fe=58.69000),
        pseudos         = ['Fe.pbe-nd-rrkjus.UPF'],
        elem            = ['Fe','Fe'],
        pos             = [[2.070000000, 0.000000000, 0.000000000],    
                           [0.000000000, 0.000000000, 0.000000000]],
        pos_specifier   = 'angstrom',
        kgrid           = np.array((1,1,1)),
        kshift          = np.array((1,1,1)),
        starting_ns_eigenvalue = {(1,2,1) : 0.0,
                                  (2,2,1) : 0.0476060,
                                  (3,2,1) : 0.0476060,
                                  (4,2,1) : 0.9654373,
                                  (5,2,1) : 0.9954307,},
        celldm                 = {1 : 15 },
        starting_magnetization = {1 : 0.9},
        hubbard_u              = {1 : 3.1},
        )

    pwg = pw.copy()
    pwg.standardize_types()

    generations[infile] = pw

    pw2 = compositions[infile].copy()
    pw2.standardize_types()
    check_pw_same(pwg,pw2,'generate','compose')
    pw3 = reads[infile]
    check_pw_same(pwg,pw3,'generate','read')
    if os.path.exists(write_path):
        os.remove(write_path)
    #end if
    pw.write(write_path)
    pw4 = PwscfInput(write_path)
    check_pw_same(pwg,pw3,'generate','write')


    # restore logging function
    restore_nexus_log()